I am working on a bottom navigation bar, but I am not getting perfectly bottom navigation bar.
My MainActivity
class:
public class MainActivity extends AppCompatActivity {
private static final String SELECTED_ITEM = "selected_item";
private BottomNavigationView bottomNavigationView;
private Toolbar toolbar;
private MenuItem menuItemSelected;
private int mMenuItemSelected;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
toolbar = (Toolbar) findViewById(R.id.toolbar);
setSupportActionBar(toolbar);
bottomNavigationView = (BottomNavigationView) findViewById(R.id.bottom_navigation);
bottomNavigationView.setOnNavigationItemSelectedListener(new BottomNavigationView.OnNavigationItemSelectedListener() {
@Override
public boolean onNavigationItemSelected(@NonNull MenuItem item) {
selectFragment(item);
return true;
}
});
//Always load first fragment as default
FragmentTransaction fragmentTransaction = getSupportFragmentManager().beginTransaction();
fragmentTransaction.replace(R.id.frameLayout, new AnnouncementFragment());
fragmentTransaction.commit();
if (savedInstanceState != null) {
mMenuItemSelected = savedInstanceState.getInt(SELECTED_ITEM, 0);
menuItemSelected = bottomNavigationView.getMenu().findItem(mMenuItemSelected);
} else {
menuItemSelected = bottomNavigationView.getMenu().getItem(0);
}
selectFragment(menuItemSelected);
}
private void selectFragment(MenuItem item) {
Fragment fragment = null;
Class fragmentClass;
switch (item.getItemId()) {
case R.id.action_announcement:
fragmentClass = AnnouncementFragment.class;
break;
case R.id.action_menu:
fragmentClass = MenuFragment.class;
break;
case R.id.action_menu_reports:
fragmentClass = ReportFragment.class;
break;
case R.id.action_setting:
fragmentClass = SettingFragment.class;
break;
default:
fragmentClass = AnnouncementFragment.class;
}
try {
fragment = (Fragment) fragmentClass.newInstance();
} catch (Exception e) {
e.printStackTrace();
}
FragmentManager fragmentManager = getSupportFragmentManager();
fragmentManager.beginTransaction().replace(R.id.frameLayout, fragment).commit();
}
@Override
protected void onSaveInstanceState(Bundle outState) {
outState.putInt(SELECTED_ITEM, mMenuItemSelected);
super.onSaveInstanceState(outState);
}
And my back pressed also not working properly:
@Override
public void onBackPressed() {
MenuItem homeItem = bottomNavigationView.getMenu().getItem(0);
if (mMenuItemSelected != homeItem.getItemId()) {
selectFragment(homeItem);
} else {
super.onBackPressed();
}
}
How should I do that because bottom menu has uneven distribution on bar. How to properly maintain the menu space without uneven distribution.
Here I am attaching my result which I obtain on AVD
Try removing this: android:windowSoftInputMode="adjustResize" from AndroidManifest. xml This should help. You have 3 options for what to do when the keyboard shows- scroll the app such that the cursor is onscreen, resize the app in the remaining space, or nothing. Number 2 is probably the closest to what you want.
Right-click on the res folder and select Android Resource Directory. Make sure to select the resource type as a menu. Now create the bottom_menu.
According to the guidelines for Material Design
On Android, the Back button does not navigate between bottom navigation bar views.
EDIT: Material Design link no longer mentions back button behavior.
Pressing the back button you can quit the application, which is the default behavior, such as in Google Photo...
FragmentManager fragmentManager = getFragmentManager();
FragmentTransaction fragmentTransaction = fragmentManager.beginTransaction();
fragmentTransaction.replace(R.id.content, fragment);
// note: there is NOT a addToBackStack call
fragmentTransaction.commit();
...or lead the user to the home section and then, if pushed again, at the exit.
Personally I find this last pattern much better.
To get it without override onBackPressed
you need to identify the home fragment and differentiate it from all the others
navigation = (BottomNavigationView) findViewById(R.id.navigation);
navigation.setOnNavigationItemSelectedListener(new BottomNavigationView.OnNavigationItemSelectedListener() {
@Override
public boolean onNavigationItemSelected(@NonNull MenuItem item) {
switch (item.getItemId()) {
case R.id.navigation_home:
viewFragment(new HomeFragment(), FRAGMENT_HOME);
return true;
case R.id.navigation_page_1:
viewFragment(new OneFragment(), FRAGMENT_OTHER);
return true;
case R.id.navigation_page_2:
viewFragment(new TwoFragment(), FRAGMENT_OTHER);
return true;
}
return false;
}
});
What you have to do now is write the viewfragment
method that have to:
commit
If the fragment is not "home type", save it to the stack before
the commit
Add an OnBackStackChangedListener
that when the stack decreases,
(i.e. when I pressed back ), delete all the fragments that are
not "home type" (POP_BACK_STACK_INCLUSIVE) , bringing us to the home fragment
Below the full method with comments
private void viewFragment(Fragment fragment, String name){
final FragmentManager fragmentManager = getFragmentManager();
FragmentTransaction fragmentTransaction = fragmentManager.beginTransaction();
fragmentTransaction.replace(R.id.content, fragment);
// 1. Know how many fragments there are in the stack
final int count = fragmentManager.getBackStackEntryCount();
// 2. If the fragment is **not** "home type", save it to the stack
if( name.equals( FRAGMENT_OTHER) ) {
fragmentTransaction.addToBackStack(name);
}
// Commit !
fragmentTransaction.commit();
// 3. After the commit, if the fragment is not an "home type" the back stack is changed, triggering the
// OnBackStackChanged callback
fragmentManager.addOnBackStackChangedListener(new FragmentManager.OnBackStackChangedListener() {
@Override
public void onBackStackChanged() {
// If the stack decreases it means I clicked the back button
if( fragmentManager.getBackStackEntryCount() <= count){
// pop all the fragment and remove the listener
fragmentManager.popBackStack(FRAGMENT_OTHER, POP_BACK_STACK_INCLUSIVE);
fragmentManager.removeOnBackStackChangedListener(this);
// set the home button selected
navigation.getMenu().getItem(0).setChecked(true);
}
}
});
}
Try this
@Override
public void onBackPressed() {
BottomNavigationView bottomNavigationView = (BottomNavigationView) findViewById(R.id.navigation);
int seletedItemId = bottomNavigationView.getSelectedItemId();
if (R.id.home != seletedItemId) {
setHomeItem(MainActivity.this);
} else {
super.onBackPressed();
}
}
public static void setHomeItem(Activity activity) {
BottomNavigationView bottomNavigationView = (BottomNavigationView)
activity.findViewById(R.id.navigation);
bottomNavigationView.setSelectedItemId(R.id.home);
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With