0

I want to add new fragment transition when BottomNavigationView change its current fragment. I want to enter the next fragment from left to right.

I don't see this for Jetpack BottomNavigationView to add custom fragment transition animations because there are no actions available for BottomNavigationView.

Dehan Wjiesekara
  • 3,152
  • 3
  • 32
  • 46

2 Answers2

2

As per this issue:

NavigationUI follows the material design guidelines, which specifically calls [see the 'Transitions' section] for a cross fade animation between BottomNavigationView items.

Setting your own listener is indeed the correct approach if you want to deviate from the guidelines and what NavigationUI provides.

Therefore you'll want to look at the NavigationUI source code for its onNavDestinationSelected() method and make your own version that passes in what custom animations you want, calling it from your own OnNavigationItemSelectedListener.

Community
  • 1
  • 1
ianhanniballake
  • 191,609
  • 30
  • 470
  • 443
  • Might be useful to note that the bottom navigation view still needs to be set with the binding.navigationView.setupWithNavController(navController) method. Otherwise things like up behaviour won't act as expected and will lead to the navController no longer directing according to the navGraph which will cause crashes. I feel like this is something that could be made clearer in the android dev guide. – Josh Hardman Jan 11 '20 at 07:41
2

I have posted this question and I have get a great help from the answer of ianhanniballake ( The answer I accepted) to fulfil my expectation. For people who refer this Quection and answer in future I'm further add some code following to further reference and understanding. Feel free to comment if you need any help after you go through the code.

Following is my Source code in MainActivity.java" OnCreate() Method

protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
    final BottomNavigationView bottomNavigationView=findViewById(R.id.bottomNavigationView);
    final NavController navController= Navigation.findNavController(this,R.id.nav_host_fragment);
    selectedItem=R.id.firstFragment1;
    bottomNavigationView.setOnNavigationItemSelectedListener(new BottomNavigationView.OnNavigationItemSelectedListener() {
        @Override
        public boolean onNavigationItemSelected(@NonNull MenuItem item) {
            switch (item.getItemId()){
                case R.id.firstFragment1:

                    if(selectedItem != R.id.firstFragment1){
                        selectedItem = R.id.firstFragment1;
                        navController.popBackStack();
                    }
                    break;
                case R.id.secondFragment1:
                    if(selectedItem != R.id.secondFragment1) {
                        selectedItem= R.id.secondFragment1;
                        Log.d("palvision.dev", "action to first fragment");
                        navController.navigate(R.id.action_firstFragment_to_secondFragment2);
                    }
                    break;
            }
            return true;
        }
    });
}

Following is my source code in nav_graph.xml which is navigation graph.

<?xml version="1.0" encoding="utf-8"?>
<navigation xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/nav_graph"
app:startDestination="@id/firstFragment">
<fragment
    android:id="@+id/firstFragment"
    android:name="com.dehan.myapplicationnavtest.FirstFragment"
    tools:layout="@layout/fragment_first" >
    <action
        android:id="@+id/action_firstFragment_to_secondFragment2"
        app:destination="@+id/secondFragment"
        app:enterAnim="@anim/enter_from_right"
        app:exitAnim="@anim/exit_to_left"
        app:popEnterAnim="@anim/enter_from_left"
        app:popExitAnim="@anim/exit_to_right" />
</fragment>
<fragment
    android:id="@+id/secondFragment"
    android:name="com.dehan.myapplicationnavtest.SecondFragment"
    tools:layout="@layout/fragment_second" />

Following is the code for FirstFragment.java

public class FirstFragment extends Fragment {

public FirstFragment() {
    // Required empty public constructor
}


@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);

}

@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
                         Bundle savedInstanceState) {
    // Inflate the layout for this fragment
    return inflater.inflate(R.layout.fragment_first, container, false);
}

@Override
public void onViewCreated(@NonNull View view, @Nullable Bundle savedInstanceState) {
    super.onViewCreated(view, savedInstanceState);

    Toolbar toolbar=view.findViewById(R.id.toolbar);
    NavController navController= Navigation.findNavController(getActivity(),R.id.nav_host_fragment);
    AppBarConfiguration appBarConfiguration =new AppBarConfiguration.Builder(navController.getGraph()).build();

    NavigationUI.setupWithNavController(toolbar,navController,appBarConfiguration);
}
}

following is the code for SecondFragment.java

public class SecondFragment extends Fragment {

public SecondFragment() {
    // Required empty public constructor
}

@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);

}

@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
                         Bundle savedInstanceState) {
    // Inflate the layout for this fragment
    return inflater.inflate(R.layout.fragment_second, container, false);
}
}

following is the code for enter_from_right.xml which is located in anim folder. all the other animation files are also placed in anim folder.

<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android"
android:shareInterpolator="false">
<translate
    android:fromXDelta="100%" android:toXDelta="0%"
    android:fromYDelta="0%" android:toYDelta="0%"
    android:duration="400" />

following is the code for exit_to_left.xml

<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android"
android:shareInterpolator="false">
<translate
    android:fromXDelta="0%" android:toXDelta="-100%"
    android:fromYDelta="0%" android:toYDelta="0%"
    android:duration="400"/>

enter_from_left.xml

<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android"
android:shareInterpolator="false">
<translate
    android:fromXDelta="-100%" android:toXDelta="0%"
    android:fromYDelta="0%" android:toYDelta="0%"
    android:duration="400"/>

exit_to_right.xml

<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android"
android:shareInterpolator="false">
<translate
    android:fromXDelta="0%" android:toXDelta="100%"
    android:fromYDelta="0%" android:toYDelta="0%"
    android:duration="400" />

Dehan Wjiesekara
  • 3,152
  • 3
  • 32
  • 46