I created an activity with a bottom navigation bar.
I googled a lot things about it but now I don't know how to handle this exactly.
Before, I just started another activity when the user clicks the bottom navigation but I think it's not good.
How can I switch between the tabs?
Do I have to work with fragments? And what about 'setContentView(int layoutResID)'? How can I do that? I'm confused...
private BottomNavigationView.OnNavigationItemSelectedListener mOnNavigationItemSelectedListener = new BottomNavigationView.OnNavigationItemSelectedListener() {
#Override
public boolean onNavigationItemSelected(#NonNull MenuItem item) {
switch (item.getItemId()) {
case R.id.navigation_home:
return true;
case R.id.navigation_dashboard:
startActivity(dashboardActivity);
return true;
case R.id.navigation_notifications:
startActivity(dashboardActivity);
return true;
}
return false;
}
};
Thank you very much for your help - I hope, you understood what I mean.
Activity transition is always expensive and we should switch from one activity to another only when we are switching the context. A fragment is a portion of UI in an activity. Same fragment can be used with multiple activities. Just like activity a fragment has its own lifecycle and setContentView(int layoutResID) can be set to different layout in OnCreate of fragment.
This link explains more on when to use activity or fragment.
Android developer guide on Fragments
Code path tutorial on bottom navigation views.
Please refer to :-
https://github.com/waleedsarwar86/BottomNavigationDemo
and complete explanation in
http://waleedsarwar.com/posts/2016-05-21-three-tabs-bottom-navigation/
You will get a running code with the explanation here.
Bottom Navigation View is a navigation bar introduced in android library to make it easy to switch between views with a single tap. It can although be used for almost any purpose, but is most commonly used to switch between fragments with a single tap. Its use for opening activities is somewhat absurd, since it ignores its most important functionality of switching the views with a single tap. There are many good articles and blogs out there in this regard, one of which is:
https://medium.com/#hitherejoe/exploring-the-android-design-support-library-bottom-navigation-drawer-548de699e8e0
Hope this solves your doubt..
bottomNavigationView.setOnNavigationItemSelectedListener
(new BottomNavigationView.OnNavigationItemSelectedListener() {
#Override
public boolean onNavigationItemSelected(#NonNull MenuItem item) {
Fragment selectedFragment = null;
switch (item.getItemId()) {
case R.id.action_item1:
selectedFragment = ItemOneFragment.newInstance();
FragmentTransaction transaction = getSupportFragmentManager().beginTransaction();
transaction.replace(R.id.frame_layout, selectedFragment);
transaction.commit();
// selectedFragment.getChildFragmentManager().beginTransaction();
break;
case R.id.action_item2:
selectedFragment = ItemTwoFragment.newInstance();
FragmentTransaction transactiona = getSupportFragmentManager().beginTransaction();
transactiona.replace(R.id.frame_layout, selectedFragment);
transactiona.commit();
// selectedFragment = ItemThreeFragment.newInstance();
break;
case R.id.action_item3:
// selectedFragment = ItemOneFragment.newInstance();
Intent intent=new Intent(MainView.this, YoutActivityLive.class);
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
startActivity(intent);
// selectedFragment = ItemTwoFragment.newInstance();
break;
case R.id.action_item5:
selectedFragment = ItemOneFragment.newInstance();
FragmentTransaction transactionb = getSupportFragmentManager().beginTransaction();
transactionb.replace(R.id.frame_layout, selectedFragment);
transactionb.commit();
// selectedFragment = ItemFiveFragment.newInstance();
break;
}
return true;
}
});
Related
I am trying to build app with BottomNavigationView and I set setOnItemSelectedListener() method to bottom navigation so I can do what I want when user select one of the menu in bottom navigation.
everything is good when I don't set setOnItemSelectedListener(), but when I set setOnItemSelectedListener() method then the fragment is not updated automatically when user select the bottom navigation menu.
I consider if that do i have to handle fragment transaction manually when I set this method?
thanks ^^
Yes. You need to manually replace the fragment item on onNavigationItemSelected
Example:
private BottomNavigationView.OnNavigationItemSelectedListener navListener = new BottomNavigationView.OnNavigationItemSelectedListener() {
#Override
public boolean onNavigationItemSelected(#NonNull MenuItem item) {
// By using switch we can easily get
// the selected fragment
// by using there id.
Fragment selectedFragment = null;
switch (item.getItemId()) {
case R.id.algorithm:
selectedFragment = new AlgorithmFragment();
break;
case R.id.course:
selectedFragment = new CourseFragment();
break;
case R.id.profile:
selectedFragment = new ProfileFragment();
break;
}
// It will help to replace the
// one fragment to other.
getSupportFragmentManager()
.beginTransaction()
.replace(R.id.fragment_container, selectedFragment)
.commit();
return true;
}
};
You can find a good tutorial here: https://www.geeksforgeeks.org/bottomnavigationview-inandroid/
In my app I have 5 fragments. In order to switch between them i use bottom navigation bar.
Also, i need to open activities from my fragments, but when I open new activity it opens in each of the fragments. (I mean over the fragments, in each case)
How to make the activity open in one case?
My code:
private BottomNavigationView.OnNavigationItemSelectedListener mOnNavigationItemSelectedListener
= new BottomNavigationView.OnNavigationItemSelectedListener() {
#Override
public boolean onNavigationItemSelected(#NonNull MenuItem item) {
Fragment fragment = null;
switch (item.getItemId()) {
case R.id.nav_home:
fragmentManager.beginTransaction().hide(active).show(fragment1).commit();
active = fragment1;
return true;
case R.id.nav_bookmark:
fragmentManager.beginTransaction().hide(active).show(fragment2).commit();
active = fragment2;
return true;
case R.id.nav_blog:
fragmentManager.beginTransaction().hide(active).show(fragment3).commit();
active = fragment3;
return true;
case R.id.nav_notification:
fragmentManager.beginTransaction().hide(active).show(fragment4).commit();
active = fragment4;
return true;
case R.id.nav_account:
fragmentManager.beginTransaction().hide(active).show(fragment5).commit();
active = fragment5;
return true;
}
return false;
}
};
Thanks!
This is clearly a FragmentManager issue - and not an Activity issue.
Instead .hide().show() use .replace().
For reference, see the documentation.
According to the Android documentation, an activity is always placed on top of the current activity stack.
So if you have the MainActivity with the BottomNavigationView and the fragments, starting a new Activity will open the activity above the MainActivity with the BottomNavigationView. So it is not possible to open an Activity only in one of the BottomNavigationView Fragments.
To achieve the desired behaviour, consider using another Fragment instead.
I have a setup of 3 Fragments inside my main activity and want to navigate them using the BottomNavigationView. I want to add them once and then just switch between them without actually destroying the Fragments. Everything works fine except that the first fragment added to the SupportFragmentManager always disappears (tried changing the order so the problem is not with the Fragments themselves). Actually, it doesn't disappear but the last Fragment that occupied the container shows up.
Eg. I go to position 3, Fragment 3 shows up in the container and then click on position 1, Fragment 3 will still occupy the container. But if I tap position 2 Fragment 2 will appear. How I'm adding the Fragments:
FragmentTransaction ft = getSupportFragmentManager().beginTransaction();
ft.add(R.id.container, fragment1); //whatever gets added here ends up being invisible
ft.commitAllowingStateLoss();
ft = getSupportFragmentManager().beginTransaction();
ft.add(R.id.container, fragment2);
ft.commitAllowingStateLoss();
ft = getSupportFragmentManager().beginTransaction();
ft.add(R.id.container, fragment3);
ft.commitAllowingStateLoss();
How I'm switching between them using the OnNavigationItemSelectedListener:
private BottomNavigationView.OnNavigationItemSelectedListener navigation_listener =
new BottomNavigationView.OnNavigationItemSelectedListener() {
#Override
public boolean onNavigationItemSelected(#NonNull MenuItem item) {
Fragment selectedFragment = null;
Fragment previousFragment = getSupportFragmentManager().findFragmentById(R.id.container);
switch(item.getItemId()){
case R.id.bottom_navigation_bar_position1:
selectedFragment = fragment1;
break;
case R.id.bottom_navigation_bar_position2:
selectedFragment = fragment2;
break;
case R.id.bottom_navigation_bar_position3:
selectedFragment = fragment3;
break;
}
getSupportFragmentManager().beginTransaction().hide(previousFragment).commit();
getSupportFragmentManager().beginTransaction().show(selectedFragment).commit();
return true;
}
};
The XML menu navigation:
<item
android:id="#+id/bottom_navigation_bar_position1"
android:title="Title1"
android:icon="#drawable/ic1"
/>
<item
android:id="#+id/bottom_navigation_bar_position2"
android:title="Title2"
android:icon="#drawable/ic2"
/>
<item
android:id="#+id/bottom_navigation_bar_position3"
android:title="Title3"
android:icon="#drawable/ic3"
/>
Btw. just using replace() instead of show and hide works but that's not the goal...
I've also tested whether the first added Fragment exits (and doesn't get destroyed) and it indeed exists...
Thanks!
Instead of trying to show and hide fragment I solved the problem by managing the Fragments using a ViewPager and a SectionsPageAdapter. Once you link these two, use ViewPager.setOffscreenPageLimit(3) to make sure no Fragments get destroyed. My BottomNavigationView.OnNavigationItemSelectedListener looks like this now:
private BottomNavigationView.OnNavigationItemSelectedListener navigation_listener =
new BottomNavigationView.OnNavigationItemSelectedListener() {
#Override
public boolean onNavigationItemSelected(#NonNull MenuItem item) {
switch(item.getItemId()){
case R.id.bottom_navigation_bar_position1:
tab_view_pager.setCurrentItem(0);
return true;
case R.id.bottom_navigation_bar_position2:
tab_view_pager.setCurrentItem(1);
return true;
case R.id.bottom_navigation_bar_position3:
tab_view_pager.setCurrentItem(2);
return true;
}
return false;
}
};
You have to set 0th position item selected for BottomNavigationView.OnNavigationItemSelectedListener. Find Menu bottom_navigation_bar_position1
I used this in my code, please refactor according to your needs
BottomNavigationView navigation = findViewById(R.id.navigation);
navigation.setOnNavigationItemSelectedListener(this);
Menu menu = navigation.getMenu();
this.onNavigationItemSelected(menu.findItem(R.id.navigation_doc));
I would like to get some input on the best way to structure my app's architecture when using Android's Bottom Navigation View.
Currently I define my BottomNavigationView in my MainActivity. It looks something like this.
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
BottomNavigationView bottomNavigationView = (BottomNavigationView)findViewById(R.id.bottom_navigation);
bottomNavigationView.setOnNavigationItemSelectedListener(new BottomNavigationView.OnNavigationItemSelectedListener() {
#Override
public boolean onNavigationItemSelected(#NonNull MenuItem item) {
Fragment selectedFragment = null;
switch (item.getItemId()){
case R.id.action_home:
selectedFragment = HomeFragment.newInstance();
break;
case R.id.action_search:
selectedFragment = SearchFragment.newInstance();
break;
case R.id.action_message:
selectedFragment = MessageFragment.newInstance();
break;
case R.id.action_profile:
selectedFragment = ProfileFragment.newInstance();
break;
}
FragmentTransaction transaction = getSupportFragmentManager().beginTransaction();
transaction.replace(R.id.frame_layout, selectedFragment);
transaction.commit();
return true;
}
});
//Manually displaying the first fragment - one time only
FragmentTransaction transaction = getSupportFragmentManager().beginTransaction();
transaction.replace(R.id.frame_layout, HomeFragment.newInstance());
transaction.commit();
}
The problem is that once I click on one tab, it opens up a fragment, and I would like to have those Fragments open up other Fragments/Activities (i.e:
I open the profile tab (`ProfileFragment` loads)
I click on a button from `ProfileFragment`, and from this the `SignUpFragment` loads
After running into many bugs, I've researched on how to architect my app, but i've found mixed results. Would anyone know the correct way of using a BottomNavigationView with Fragments, and in those fragments I can load more Activities/fragments. A huge thanks in advance.
enter image description hereI am developing an app in android and I want to implement a menu similar to the image, does anyone have any examples of how to do it?
Definitely you should use Fragment for each bottom navigation Item / Tab. Like FragmentHome, FragmentSearch and FragmentSettings.
To change the Fragment, add NavigationItemSelectedListener to your BottomNavigationView and change Fragment as per MenuItem selection:
BottomNavigationView bottomNavigationView = (BottomNavigationView)
findViewById(R.id.bottom_navigation_view);
bottomNavigationView.setOnNavigationItemSelectedListener
(new BottomNavigationView.OnNavigationItemSelectedListener() {
#Override
public boolean onNavigationItemSelected(#NonNull MenuItem item) {
Fragment selectedFragment = null;
switch (item.getItemId()) {
case R.id.action_item1:
selectedFragment = FragmentHome.newInstance();
break;
case R.id.action_item2:
selectedFragment = FragmentSearch.newInstance();
break;
case R.id.action_item3:
selectedFragment = FragmentSettings.newInstance();
break;
}
FragmentTransaction transaction = getSupportFragmentManager().beginTransaction();
transaction.replace(R.id.frame_layout, selectedFragment);
transaction.commit();
return true;
}
});
Here is a tutorial about: BottomNavigationView with multiple Fragments
Here is an useful link:
Android Toolbar Adding Menu Items for different fragments
Hope this will help to understand the scenario.
You can find your answer here: Which view should be used for new Material Design Bottom Navigation?
here is a github project for bottom menu: https://github.com/roughike/BottomBar
Use the SpaceNavigationView library to get the Bottom Navigation Bar similar to your required design.
https://github.com/armcha/Space-Navigation-View
Other libraries you can have a look.
https://github.com/aurelhubert/ahbottomnavigation
https://github.com/sephiroth74/Material-BottomNavigation
https://github.com/Ashok-Varma/BottomNavigation