Android 实现首页Tab切换并且支持懒加载功能详解

目录

    • [1. 添加依赖](#1. 添加依赖)
    • [2. 布局文件](#2. 布局文件)
    • [3. 创建 Fragment](#3. 创建 Fragment)
    • [4. 创建适配器](#4. 创建适配器)
    • [5. 在 MainActivity 中设置 TabLayout 和 ViewPager2](#5. 在 MainActivity 中设置 TabLayout 和 ViewPager2)

1. 添加依赖

在 build.gradle 文件中添加以下依赖:

bash 复制代码
implementation 'androidx.viewpager2:viewpager2:1.1.0-beta01'
implementation 'com.google.android.material:material:1.6.1'

2. 布局文件

在 res/layout/activity_main.xml 中创建主界面布局:

bash 复制代码
<?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"
    android:orientation="vertical">

    <com.google.android.material.tabs.TabLayout
        android:id="@+id/tabLayout"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        app:tabGravity="fill"
        app:tabMode="fixed" />

    <androidx.viewpager2.widget.ViewPager2
        android:id="@+id/viewPager2"
        android:layout_width="match_parent"
        android:layout_height="match_parent" />
</LinearLayout>

3. 创建 Fragment

创建多个 Fragment 用于展示不同的页面内容,以 HomeFragment 为例:

bash 复制代码
import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.fragment.app.Fragment;

public class HomeFragment extends Fragment {

    private boolean isLoaded = false;

    @Nullable
    @Override
    public View onCreateView(@NonNull LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
        return inflater.inflate(R.layout.fragment_home, container, false);
    }

    @Override
    public void onResume() {
        super.onResume();
        if (!isLoaded && isVisible()) {
            loadData();
            isLoaded = true;
        }
    }

    private void loadData() {
        // 这里进行数据加载操作,例如网络请求等
    }
}

对应的 fragment_home.xml 布局文件:

bash 复制代码
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:gravity="center"
    android:orientation="vertical">

    <TextView
        android:text="Home Page"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:textSize="24sp" />
</LinearLayout>

4. 创建适配器

创建一个继承自 FragmentStateAdapter 的适配器类:

bash 复制代码
import androidx.annotation.NonNull;
import androidx.fragment.app.Fragment;
import androidx.fragment.app.FragmentActivity;
import androidx.viewpager2.adapter.FragmentStateAdapter;

import java.util.ArrayList;
import java.util.List;

public class MyFragmentStateAdapter extends FragmentStateAdapter {

    private final List<Fragment> fragmentList = new ArrayList<>();

    public MyFragmentStateAdapter(@NonNull FragmentActivity fragmentActivity) {
        super(fragmentActivity);
    }

    public void addFragment(Fragment fragment) {
        fragmentList.add(fragment);
    }

    @NonNull
    @Override
    public Fragment createFragment(int position) {
        return fragmentList.get(position);
    }

    @Override
    public int getItemCount() {
        return fragmentList.size();
    }
}

5. 在 MainActivity 中设置 TabLayout 和 ViewPager2

bash 复制代码
import androidx.appcompat.app.AppCompatActivity;
import androidx.viewpager2.widget.ViewPager2;
import com.google.android.material.tabs.TabLayout;
import com.google.android.material.tabs.TabLayoutMediator;
import android.os.Bundle;
import android.graphics.drawable.Drawable;
import androidx.core.content.ContextCompat;

public class MainActivity extends AppCompatActivity {

    private TabLayout tabLayout;
    private ViewPager2 viewPager2;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        tabLayout = findViewById(R.id.tabLayout);
        viewPager2 = findViewById(R.id.viewPager2);

        MyFragmentStateAdapter adapter = new MyFragmentStateAdapter(this);
        adapter.addFragment(new HomeFragment());
        adapter.addFragment(new DiscoverFragment());
        adapter.addFragment(new ProfileFragment());

        viewPager2.setAdapter(adapter);

        new TabLayoutMediator(tabLayout, viewPager2, (tab, position) -> {
            switch (position) {
                case 0:
                    tab.setText("Home");
                    Drawable homeIcon = ContextCompat.getDrawable(this, R.drawable.ic_home);
                    tab.setIcon(homeIcon);
                    break;
                case 1:
                    tab.setText("Discover");
                    Drawable discoverIcon = ContextCompat.getDrawable(this, R.drawable.ic_discover);
                    tab.setIcon(discoverIcon);
                    break;
                case 2:
                    tab.setText("Profile");
                    Drawable profileIcon = ContextCompat.getDrawable(this, R.drawable.ic_profile);
                    tab.setIcon(profileIcon);
                    break;
            }
        }).attach();
    }
}

运行该应用后,你会看到一个带有图片和文字的 TabLayout,同时可以通过点击 Tab 或者左右滑动屏幕来切换不同的页面,并且每个 Fragment 会在第一次可见时进行数据加载,实现了懒加载的功能。

相关推荐
黎猫大侠7 分钟前
一次Android Fragment内存泄露的bug解决记录|Fragment not attach to an Activity
android·bug
袁震3 小时前
android HashMap和List该如何选择
android·hashmap·sparsearray
xiaogai_gai4 小时前
高效管理钉钉收款单数据集成到MySQL的技术方案
android·mysql·钉钉
_extraordinary_5 小时前
MySQL 索引(一)
android·数据库·mysql
gjc5925 小时前
MySQL OCP试题解析(2)
android·数据库·mysql·开闭原则
Watink Cpper6 小时前
[Linux]多线程(二)原生线程库---pthread库的使用
android·linux·运维·原生线程库·pthread库
笨鸭先游11 小时前
前台--Android开发
android
fareast_mzh11 小时前
Lightweight App Alternatives
android
pq113_615 小时前
OrangePi Zero 3学习笔记(Android篇)4 - eudev编译(获取libudev.so)
android·笔记·学习
鸿蒙布道师19 小时前
鸿蒙NEXT开发动画案例3
android·ios·华为·harmonyos·鸿蒙系统·arkui·huawei