安卓动态设置BottomNavigationView底部导航

前言:解决项目中有多个端的情况

效果图:
在这里插入图片描述
1:app\build.gradle中添加依赖:
android x :

 implementation 'androidx.appcompat:appcompat:1.1.0'

非android x(注意版本号对应) :

 implementation 'com.android.support:design:28.0.0'

2:MainActivity:

public class MainActivity extends AppCompatActivity implements BottomNavigationView.OnNavigationItemSelectedListener {

    private BottomNavigationView navigation;
    //默认选中第一个
    private int defaultSelectedPosition = 0;
    private Fragment[] fragments;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        navigation = this.findViewById(R.id.navigation);
        initFragments();
    }

    /**
     * 初始化导航栏参数
     */
    private void initFragments() {

        //去掉不显示图片默认颜色
        navigation.setItemIconTintList(null);
        //选中、未选中颜色
        int[][] states = new int[][]{
                new int[]{-android.R.attr.state_checked},//(注意-不能少)未选中状态颜色
                new int[]{android.R.attr.state_checked}};
        int[] colors = new int[]{
                getResources().getColor(R.color.unsel_color),//未选中状态颜色
                getResources().getColor(R.color.sel_color)};//选中状态颜色
        //公用fragment
        Fragment3Activity fragment3 = new Fragment3Activity();
        Fragment1Activity fragment1 = new Fragment1Activity();
        //自行判断加载对应导航栏
        String value = getIntent().getStringExtra("value");
        if (TextUtils.isEmpty(value)) {
            navigation.inflateMenu(R.menu.navigation1);
            MenuItem home1 = navigation.getMenu().findItem(R.id.navigation_homefirst);
            MenuItem home2 = navigation.getMenu().findItem(R.id.navigation_homesecond);
            MenuItem home3 = navigation.getMenu().findItem(R.id.navigation_homethird);
            home1.setIcon(R.drawable.home_one_shape);
            home2.setIcon(R.drawable.home_two_shape);
            home3.setIcon(R.drawable.home_three_shape);
            Fragment2Activity fragment2 = new Fragment2Activity();
            //装入fragment集合中
            fragments = new Fragment[]{fragment1, fragment2, fragment3};
        } else {
            //医生端
            navigation.inflateMenu(R.menu.navigation2);
            MenuItem home1 = navigation.getMenu().findItem(R.id.navigation_homefirst);
            MenuItem home2 = navigation.getMenu().findItem(R.id.navigation_homesecond);
            MenuItem home3 = navigation.getMenu().findItem(R.id.navigation_homethird);
            MenuItem home4 = navigation.getMenu().findItem(R.id.navigation_homefourth);
            home1.setIcon(R.drawable.home_one_shape);
            home2.setIcon(R.drawable.home_two_shape);
            home3.setIcon(R.drawable.home_three_shape);
            home4.setIcon(R.drawable.home_four_shape);
            Fragment4Activity fragment4 = new Fragment4Activity();
            Fragment5Activity fragment5 = new Fragment5Activity();
            Fragment6Activity fragment6 = new Fragment6Activity();
            //装入fragment集合中
            fragments = new Fragment[]{fragment3, fragment4, fragment5, fragment6};
        }
        ColorStateList csl = new ColorStateList(states, colors);
        navigation.setItemTextColor(csl);
        //切换监听事件
        navigation.setOnNavigationItemSelectedListener(this);
        getSupportFragmentManager()
                .beginTransaction()
                .add(R.id.tb, fragment1)//开启第一个碎片
                .show(fragment1)
                .commit();
    }

    @Override
    public boolean onNavigationItemSelected(@NonNull MenuItem item) {
        switch (item.getItemId()) {
            case R.id.navigation_homefirst:
                if (0 != defaultSelectedPosition) {
                    setDefaultFragment(defaultSelectedPosition, 0);
                    defaultSelectedPosition = 0;
                }
                return true;
            case R.id.navigation_homesecond:
                if (1 != defaultSelectedPosition) {
                    setDefaultFragment(defaultSelectedPosition, 1);
                    defaultSelectedPosition = 1;
                }
                return true;
            case R.id.navigation_homethird:
                if (2 != defaultSelectedPosition) {
                    setDefaultFragment(defaultSelectedPosition, 2);
                    defaultSelectedPosition = 2;
                }
                return true;
            case R.id.navigation_homefourth:
                if (3 != defaultSelectedPosition) {
                    setDefaultFragment(defaultSelectedPosition, 3);
                    defaultSelectedPosition = 3;
                }
                return true;
        }
        return false;
    }

    /**
     * 切换Fragment
     *
     * @param lastIndex 上个显示Fragment的索引
     * @param index     需要显示的Fragment的索引
     */
    private void setDefaultFragment(int lastIndex, int index) {
        FragmentTransaction transaction = getSupportFragmentManager().beginTransaction();
        transaction.hide(fragments[lastIndex]);
        if (!fragments[index].isAdded()) {
            transaction.add(R.id.tb, fragments[index]);
        }
        //需要展示fragment下标的位置
        //commit:安排该事务的提交。这一承诺不会立即发生;它将被安排在主线程上,以便在线程准备好的时候完成。
        //commitAllowingStateLoss:与 commit类似,但允许在活动状态保存后执行提交。这是危险的,因为如果Activity需要从其状态恢复,
        //那么提交就会丢失,因此,只有在用户可以意外地更改UI状态的情况下,才可以使用该提交
        transaction.show(fragments[index]).commit();
    }
}

对应布局activity_main:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:layout_width="match_parent"
    android:layout_height="match_parent">

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:orientation="vertical">

        <FrameLayout
            android:id="@+id/tb"
            android:layout_width="match_parent"
            android:layout_height="0dp"
            android:layout_weight="1" />

        <View android:layout_width="match_parent"
            android:layout_height="0.5dp"
            android:background="@color/unsel_color"/>

        <!-- itemBackground:水波纹效果-->
        <com.google.android.material.bottomnavigation.BottomNavigationView
            android:id="@+id/navigation"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:background="@color/white_color"
            app:itemBackground="@null"
            app:labelVisibilityMode="labeled" />

    </LinearLayout>
</LinearLayout>

对应的Fragment1Activity(一共6个这里例举一个):

ublic class Fragment1Activity extends Fragment {

    private View mView;

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
        if (mView != null) {
            ViewGroup parent = (ViewGroup) mView.getParent();
            if (parent != null) {
                parent.removeView(mView);
            }
        } else {
            mView = inflater.inflate(R.layout.activity_fragment1, container, false);
        }
        return mView;
    }
}

3:资源相关
①:颜色值

<color name="sel_color">#31AADE</color>
<color name="unsel_color">#999999</color>
<color name="white_color">#ffffff</color>

②:drawable
home_one_shape至home_five_shape.xml是一致的

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">

    <item android:drawable="@drawable/home1_sel" android:state_checked="true" />
    <item android:drawable="@drawable/home1_unsel" android:state_checked="false" />
    
</selector>

③:drawable-xxhdpi图片资源这里不贴出
home1_sel选中图片,home1_unsel未选中图片

④:res目录下新建菜单menu文件夹,如下图
在这里插入图片描述
navigation1.xml:

<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:android="http://schemas.android.com/apk/res/android">
    <item
        android:id="@+id/navigation_homefirst"
        android:title="@string/home_title1" />

    <item
        android:id="@+id/navigation_homesecond"
        android:title="@string/home_title2" />

    <item
        android:id="@+id/navigation_homethird"
        android:title="@string/home_title3" />
</menu>

navigation2.xml:

<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:android="http://schemas.android.com/apk/res/android">
    <item
        android:id="@+id/navigation_homefirst"
        android:title="@string/home1_title" />

    <item
        android:id="@+id/navigation_homesecond"
        android:title="@string/home2_title" />

    <item
        android:id="@+id/navigation_homethird"
        android:title="@string/home3_title" />

    <item
        android:id="@+id/navigation_homefourth"
        android:title="@string/home4_title" />
</menu>

对应的文字:

<string name="home_title1">骑手端1</string>
<string name="home_title2">骑手端2</string>
<string name="home_title3">骑手端3</string>
    
<string name="home1_title">用户端1</string>
<string name="home2_title">用户端2</string>
<string name="home3_title">用户端3</string>
<string name="home4_title">用户端4</string>

结尾小插曲:如何防止切换时文字一大一小?
解决:style下添加:

<dimen name="design_bottom_navigation_active_text_size">12sp</dimen>
<dimen name="design_bottom_navigation_text_size">12sp</dimen>

猜你喜欢

转载自blog.csdn.net/qq_34536167/article/details/104577090