原生实现办法

成果展示

准备工作

指示器包引入

1
2
3
//圆形指示器
//https://github.com/ongakuer/CircleIndicator
implementation 'me.relex:circleindicator:2.1.6'

普通Fragment 封装

BaseFragment,BaseCommonFragment,BaseViewModelFragment

具体的翻代码。

展示Activity

xml

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
<?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">

<!--左右滚动控件-->
<androidx.viewpager.widget.ViewPager
android:id="@+id/list"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_weight="1" />

<!--指示器-->
<me.relex.circleindicator.CircleIndicator
android:id="@+id/indicator"
android:layout_width="match_parent"
android:layout_height="@dimen/guide_indicator_height"
app:ci_drawable="@drawable/shape_color_primary"
app:ci_drawable_unselected="@drawable/shape_circle_light_grey" />
</LinearLayout>

Activity

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
import androidx.appcompat.app.AppCompatActivity;

import android.os.Bundle;

import com.example.superutils.statusbar.SuperStatusBarUtil;
import com.example.testandroid.R;
import com.example.testandroid.activity.BaseViewModelActivity;
import com.example.testandroid.component.guide.adapter.GuideAdapter;
import com.example.testandroid.databinding.ActivityGuideBinding;

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

public class GuideActivity extends BaseViewModelActivity<ActivityGuideBinding> {

private GuideAdapter adapter;

@Override
protected void initDatum() {
super.initDatum();

//状态栏设置
SuperStatusBarUtil.myStatusBar(getHostActivity());

//创建适配器
adapter = new GuideAdapter(getHostActivity(),getSupportFragmentManager());
//准备数据
List<Integer> datum = new ArrayList<>();
datum.add(R.drawable.img);
datum.add(R.drawable.img);
datum.add(R.drawable.img);
datum.add(R.drawable.img);

//将数据设置到适配器
adapter.setDatum(datum);

//把适配器(数据)设置到控件
binding.list.setAdapter(adapter);


//让指示器根据列表配合工作
binding.indicator.setViewPager(binding.list);

//适配器注册数据源观察者
adapter.registerDataSetObserver(binding.indicator.getDataSetObserver());

}
}

适配器

封装好的父适配器

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
import android.content.Context;

import androidx.annotation.NonNull;
import androidx.fragment.app.FragmentManager;
import androidx.fragment.app.FragmentStatePagerAdapter;

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

/**
* 通用的Adapter
*/
public abstract class BaseFragmentStatePagerAdapter<T> extends FragmentStatePagerAdapter {

private final Context context;
protected List<T> datum = new ArrayList<>();

public BaseFragmentStatePagerAdapter(Context context, @NonNull FragmentManager fm) {
super(fm);
this.context = context;
}


/**
* 有多少个Fragment
* @return
*/
@Override
public int getCount() {
return datum.size();
}

public T getData(int position){
return datum.get(position);
}

public void setDatum(List<T> datum) {
if (datum != null && datum.size() > 0){
this.datum.clear();
this.datum.addAll(datum);

//通知控件我的数据改变了
notifyDataSetChanged();
}
}


}

这个轮播图的适配器

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
import android.content.Context;

import androidx.annotation.NonNull;
import androidx.fragment.app.Fragment;
import androidx.fragment.app.FragmentManager;


import com.example.testandroid.adapter.BaseFragmentStatePagerAdapter;
import com.example.testandroid.component.guide.fragment.GuideFragment;

/**
* ViewPage的适配器
*/

public class GuideAdapter extends BaseFragmentStatePagerAdapter<Integer> {

public GuideAdapter(Context context, @NonNull FragmentManager fm) {
super(context, fm);
}

/**
* 返回当前位置Fragment
* @param position
* @return
*/
@NonNull
@Override
public Fragment getItem(int position) {
return GuideFragment.newInstance(getData(position));
}

}

技术总结

轮播图其实就是两个:上面轮播的View 和下面的指示器。

轮播的View:可以是图片,可以是ViewPage

指示器我们就直接用三方库