public classBannerLayout extendsRelativeLayout {
privateViewPager mViewPager; // 轮播容器// 指示器(圆点)容器privateLinearLayout indicatorContainer;
privateDrawable unSelectedDrawable;
privateDrawable selectedDrawable;
private intWHAT_AUTO_PLAY= 1000;
private booleanisAutoPlay= true; // 自动轮播private intitemCount;
private intselectedIndicatorColor= 0xffff0000;
private intunSelectedIndicatorColor= 0x88888888;
private inttitleBGColor= 0X33000000;
private inttitleColor= 0Xffffffff;
privateShape indicatorShape= Shape.oval;
private intselectedIndicatorHeight= 20;
private intselectedIndecatorWidth= 20;
private intunSelectedIndicatorHeight= 20;
private intunSelectedIndecatorWidth= 20;
private intautoPlayDuration= 4000;
private intscrollDuration= 900;
// 指示器中点和点之间的距离private intindicatorSpace= 15;
// 指示器整体的设置private intindicatorMargin= 20;
private static final inttitlePadding= 20;
private intdefaultImage;
private enumShape {
// 矩形 或 圆形的指示器rect, oval}
privateOnBannerItemClickListener mOnBannerItemClickListener;
privateHandler mHandler= newHandler(newHandler.Callback() {
@Overridepublic booleanhandleMessage(Message msg) {
if(msg.what== WHAT_AUTO_PLAY) {
if(mViewPager!= null) {
mViewPager.setCurrentItem(mViewPager.getCurrentItem() + 1, true);
mHandler.sendEmptyMessageDelayed(WHAT_AUTO_PLAY, autoPlayDuration);
}
}
return false;
}
});
publicBannerLayout(Context context) {
super(context);
init(null, 0);
}
publicBannerLayout(Context context, AttributeSet attrs) {
super(context, attrs);
init(attrs, 0);
}
publicBannerLayout(Context context, AttributeSet attrs, intdefStyleAttr) {
super(context, attrs, defStyleAttr);
init(attrs, defStyleAttr);
}
private voidinit(AttributeSet attrs, intdefStyleAttr) {
TypedArray array = getContext().obtainStyledAttributes(attrs, R.styleable.BannerLayoutStyle, defStyleAttr, 0);
selectedIndicatorColor= array.getColor(R.styleable.BannerLayoutStyle_selectedIndicatorColor, selectedIndicatorColor);
unSelectedIndicatorColor= array.getColor(R.styleable.BannerLayoutStyle_unSelectedIndicatorColor, unSelectedIndicatorColor);
titleBGColor= array.getColor(R.styleable.BannerLayoutStyle_titleBGColor, titleBGColor);
titleColor= array.getColor(R.styleable.BannerLayoutStyle_titleColor, titleColor);
intshape = array.getInt(R.styleable.BannerLayoutStyle_indicatorShape, Shape.oval.ordinal());
for(Shape shape1 : Shape.values()) {
if(shape1.ordinal() == shape) {
indicatorShape= shape1;
break;
}
}
selectedIndecatorWidth= (int) array.getDimension(R.styleable.BannerLayoutStyle_selectedIndicatorWidth, selectedIndecatorWidth);
selectedIndicatorHeight= (int) array.getDimension(R.styleable.BannerLayoutStyle_selectedIndicatorHeight, selectedIndicatorHeight);
unSelectedIndecatorWidth= (int) array.getDimension(R.styleable.BannerLayoutStyle_unSelectedIndicatorWidth, unSelectedIndecatorWidth);
unSelectedIndicatorHeight= (int) array.getDimension(R.styleable.BannerLayoutStyle_unSelectedIndicatorHeight, unSelectedIndicatorHeight);
indicatorSpace= (int) array.getDimension(R.styleable.BannerLayoutStyle_indicatorSpace, indicatorSpace);
indicatorMargin= (int) array.getDimension(R.styleable.BannerLayoutStyle_indicatorMargin, indicatorMargin);
autoPlayDuration= array.getInt(R.styleable.BannerLayoutStyle_autoPlayDuration, autoPlayDuration);
scrollDuration= array.getInt(R.styleable.BannerLayoutStyle_scrollDuration, scrollDuration);
isAutoPlay= array.getBoolean(R.styleable.BannerLayoutStyle_isAutoPlay, isAutoPlay);
defaultImage= array.getResourceId(R.styleable.BannerLayoutStyle_defaultImage, defaultImage);
array.recycle();
LayerDrawable unSelectedLayerDrawable;
LayerDrawable selectedLayerDrawable;
GradientDrawable unSelectedGradientDrawable = newGradientDrawable();
GradientDrawable selectedGradientDtawbale = newGradientDrawable();
switch(indicatorShape) {
caserect:
unSelectedGradientDrawable.setShape(GradientDrawable.RECTANGLE);
selectedGradientDtawbale.setShape(GradientDrawable.RECTANGLE);
break;
caseoval:
unSelectedGradientDrawable.setShape(GradientDrawable.OVAL);
selectedGradientDtawbale.setShape(GradientDrawable.OVAL);
break;
}
unSelectedGradientDrawable.setColor(unSelectedIndicatorColor);
unSelectedGradientDrawable.setSize(unSelectedIndecatorWidth, unSelectedIndicatorHeight);
unSelectedLayerDrawable = newLayerDrawable(newDrawable[]{unSelectedGradientDrawable});
unSelectedDrawable= unSelectedLayerDrawable;
selectedGradientDtawbale.setColor(selectedIndicatorColor);
selectedGradientDtawbale.setSize(selectedIndecatorWidth, selectedIndicatorHeight);
selectedLayerDrawable = newLayerDrawable(newDrawable[]{selectedGradientDtawbale});
selectedDrawable= selectedLayerDrawable;
}
/*** 添加本地图片**@paramviewRes图片id集合*@paramtitles标题集合,可空*/public voidsetViewRes(List viewRes, List titles) {
List views = newArrayList<>();
itemCount= viewRes.size();
if(titles != null&& titles.size() != viewRes.size()) {
throw newIllegalStateException("views.size() != titles.size()");
}
// 把数量拼凑到三个以上if(itemCount< 1) {
throw newIllegalStateException("item count not equal zero");
} else if(itemCount< 2) {
views.add(getFrameLayoutView(viewRes.get(0), titles != null? titles.get(0) : null, 0));
views.add(getFrameLayoutView(viewRes.get(0), titles != null? titles.get(0) : null, 0));
views.add(getFrameLayoutView(viewRes.get(0), titles != null? titles.get(0) : null, 0));
} else if(itemCount< 3) {
views.add(getFrameLayoutView(viewRes.get(0), titles != null? titles.get(0) : null, 0));
views.add(getFrameLayoutView(viewRes.get(1), titles != null? titles.get(1) : null, 1));
views.add(getFrameLayoutView(viewRes.get(0), titles != null? titles.get(0) : null, 0));
views.add(getFrameLayoutView(viewRes.get(1), titles != null? titles.get(1) : null, 1));
} else{
for(inti = 0; i < viewRes.size(); i++) {
views.add(getFrameLayoutView(viewRes.get(i), titles != null? titles.get(i) : null, i));
}
}
setViews(views);
}
//添加网络图片路径public voidsetViewUrls(Context context,List urls, List titles) {
List views = newArrayList<>();
itemCount= urls.size();
Log.e("TAG",titles.size()+"---90---"+urls.size());
if(titles != null&& titles.size() != itemCount) {
throw newIllegalStateException("views.size() != titles.size()");
}
//主要是解决当item为小于3个的时候滑动有问题,这里将其拼凑成3个以上if(itemCount< 1) {//当item个数0throw newIllegalStateException("item count not equal zero");
} else if(itemCount< 2) { //当item个数为1views.add(getFrameLayoutView(context,urls.get(0), titles != null? titles.get(0) : null, 0));
views.add(getFrameLayoutView(context,urls.get(0), titles != null? titles.get(0) : null, 0));
views.add(getFrameLayoutView(context,urls.get(0), titles != null? titles.get(0) : null, 0));
} else if(itemCount< 3) {//当item个数为2views.add(getFrameLayoutView(context,urls.get(0), titles != null? titles.get(0) : null, 0));
views.add(getFrameLayoutView(context,urls.get(1), titles != null? titles.get(1) : null, 1));
views.add(getFrameLayoutView(context,urls.get(0), titles != null? titles.get(0) : null, 0));
views.add(getFrameLayoutView(context,urls.get(1), titles != null? titles.get(1) : null, 1));
} else{
for(inti = 0; i < urls.size(); i++) {
views.add(getFrameLayoutView(context,urls.get(i), titles != null? titles.get(i) : null, i));
}
}
setViews(views);
}
private voidsetViews(finalList views) {
mViewPager= newViewPager(getContext());
addView(mViewPager);
setSliderTransformDuration(scrollDuration);
//初始化indicatorContainerindicatorContainer= newLinearLayout(getContext());
indicatorContainer.setGravity(Gravity.CENTER_VERTICAL);
LayoutParams params = newLayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);
// 设置 指示点的位置 ALIGN_PARENT_RIGHT表示居右 CENTER_HORIZONTAL表示居中params.addRule(RelativeLayout.ALIGN_PARENT_RIGHT);
params.addRule(RelativeLayout.ALIGN_PARENT_BOTTOM);
//设置marginparams.setMargins(indicatorMargin, indicatorMargin, indicatorMargin, indicatorMargin);
//添加指示器容器布局到SliderLayoutaddView(indicatorContainer, params);
//初始化指示器,并添加到指示器容器布局for(inti = 0; i < itemCount; i++) {
ImageView indicator = newImageView(getContext());
indicator.setLayoutParams(newViewGroup.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT));
indicator.setPadding(indicatorSpace, indicatorSpace, indicatorSpace, indicatorSpace);
indicator.setImageDrawable(unSelectedDrawable);
indicatorContainer.addView(indicator);
}
LoopPagerAdapter pagerAdapter = newLoopPagerAdapter(views);
mViewPager.setAdapter(pagerAdapter);
//设置当前item到Integer.MAX_VALUE中间的一个值,看起来像无论是往前滑还是往后滑都是ok的//如果不设置,用户往左边滑动的时候已经划不动了inttargetItemPosition = Integer.MAX_VALUE/ 2- Integer.MAX_VALUE/ 2% itemCount;
mViewPager.setCurrentItem(targetItemPosition);
switchIndicator(targetItemPosition % itemCount);
mViewPager.addOnPageChangeListener(newViewPager.SimpleOnPageChangeListener() {
@Overridepublic voidonPageSelected(intposition) {
switchIndicator(position % itemCount);
}
});
startAutoPlay();
}
/*** 开始自动轮播*/public voidstartAutoPlay() {
stopAutoPlay(); // 避免重复消息if(isAutoPlay) {
mHandler.sendEmptyMessageDelayed(WHAT_AUTO_PLAY, autoPlayDuration);
}
}
@Overrideprotected voidonWindowVisibilityChanged(intvisibility) {
super.onWindowVisibilityChanged(visibility);
if(visibility == VISIBLE) {
startAutoPlay();
} else{
stopAutoPlay();
}
}
/*** 停止自动轮播*/public voidstopAutoPlay() {
if(isAutoPlay) {
mHandler.removeMessages(WHAT_AUTO_PLAY);
}
}
private voidsetSliderTransformDuration(intscrollDuration) {
try{
Field mScroller = ViewPager.class.getDeclaredField("mScroller");
mScroller.setAccessible(true);
FixedSpeedScroller fixedSpeedScroller = newFixedSpeedScroller(mViewPager.getContext(), null, scrollDuration);
mScroller.set(mViewPager, fixedSpeedScroller);
} catch(Exception e) {
e.printStackTrace();
}
}
@Overridepublic booleandispatchTouchEvent(MotionEvent ev) {
switch(ev.getAction()) {
caseMotionEvent.ACTION_DOWN:
stopAutoPlay();
break;
caseMotionEvent.ACTION_CANCEL:
caseMotionEvent.ACTION_UP:
startAutoPlay();
break;
}
return super.dispatchTouchEvent(ev);
}
/*** 切换指示器状态**@paramcurrentPosition当前位置*/private voidswitchIndicator(intcurrentPosition) {
for(inti = 0; i < indicatorContainer.getChildCount(); i++) {
((ImageView) indicatorContainer.getChildAt(i)).setImageDrawable(i == currentPosition ? selectedDrawable: unSelectedDrawable);
}
}
public voidsetOnBannerItemClickListener(OnBannerItemClickListener onBannerItemClickListener) {
this.mOnBannerItemClickListener= onBannerItemClickListener;
}
@NonNullprivateFrameLayout getFrameLayoutView(Context context, String url, String title, final intposition) {
FrameLayout frameLayout = newFrameLayout(getContext());
FrameLayout.LayoutParams layoutParams = newFrameLayout.LayoutParams(LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.WRAP_CONTENT);
layoutParams.gravity= Gravity.CENTER;
ImageView imageView = newImageView(getContext());
frameLayout.addView(imageView);
frameLayout.setOnClickListener(newOnClickListener() {
@Overridepublic voidonClick(View v) {
if(mOnBannerItemClickListener!= null) {
mOnBannerItemClickListener.onItemClick(position);
}
}
});
imageView.setScaleType(ImageView.ScaleType.CENTER_CROP);
if(defaultImage!= 0){
Glide.with(getContext()).load(url).placeholder(defaultImage).centerCrop().into(imageView);
}else{
Glide.with(getContext()).load(url).centerCrop().into(imageView);
}
if(!TextUtils.isEmpty(title)) {
TextView textView = newTextView(getContext());
textView.setText(title);
textView.setTextColor(titleColor);
textView.setPadding(titlePadding, titlePadding, titlePadding, titlePadding);
textView.setBackgroundColor(titleBGColor);
textView.getPaint().setFakeBoldText(true);
layoutParams.gravity= Gravity.BOTTOM;
frameLayout.addView(textView, layoutParams);
}
returnframeLayout;
}
@NonNullprivateFrameLayout getFrameLayoutView(Integer res, String title, final intposition) {
FrameLayout frameLayout = newFrameLayout(getContext());
FrameLayout.LayoutParams layoutParams = newFrameLayout.LayoutParams(LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.WRAP_CONTENT);
layoutParams.gravity= Gravity.CENTER;
ImageView imageView = newImageView(getContext());
frameLayout.addView(imageView);
frameLayout.setOnClickListener(newOnClickListener() {
@Overridepublic voidonClick(View v) {
if(mOnBannerItemClickListener!= null) {
mOnBannerItemClickListener.onItemClick(position);
}
}
});
imageView.setScaleType(ImageView.ScaleType.CENTER_CROP);
Glide.with(getContext()).load(res).centerCrop().into(imageView);
if(!TextUtils.isEmpty(title)) {
TextView textView = newTextView(getContext());
textView.setText(title);
textView.setTextColor(titleColor);
textView.setPadding(titlePadding, titlePadding, titlePadding, titlePadding);
textView.setBackgroundColor(titleBGColor);
textView.getPaint().setFakeBoldText(true);
layoutParams.gravity= Gravity.BOTTOM;
frameLayout.addView(textView, layoutParams);
}
returnframeLayout;
}
public interfaceOnBannerItemClickListener {
voidonItemClick(intposition);
}
public classLoopPagerAdapter extendsPagerAdapter {
privateList views;
publicLoopPagerAdapter(List views) {
this.views= views;
}
@Overridepublic intgetCount() {
//Integer.MAX_VALUE = 2147483647returnInteger.MAX_VALUE;
}
@Overridepublic booleanisViewFromObject(View view, Object object) {
returnview == object;
}
@OverridepublicObject instantiateItem(ViewGroup container, intposition) {
if(views.size() > 0) {
//position % view.size()是指虚拟的position会在[0,view.size())之间循环View view = views.get(position % views.size());
if(container.equals(view.getParent())) {
container.removeView(view);
}
container.addView(view);
returnview;
}
return null;
}
@Overridepublic voiddestroyItem(ViewGroup container, intposition, Object object) {
}
}
public classFixedSpeedScroller extendsScroller {
private intmDuration= 1000;
publicFixedSpeedScroller(Context context) {
super(context);
}
publicFixedSpeedScroller(Context context, Interpolator interpolator) {
super(context, (android.view.animation.Interpolator) interpolator);
}
publicFixedSpeedScroller(Context context, Interpolator interpolator, intduration) {
this(context, interpolator);
mDuration= duration;
}
@Overridepublic voidstartScroll(intstartX, intstartY, intdx, intdy, intduration) {
// Ignore received duration, use fixed one insteadsuper.startScroll(startX, startY, dx, dy, mDuration);
}
@Overridepublic voidstartScroll(intstartX, intstartY, intdx, intdy) {
// Ignore received duration, use fixed one insteadsuper.startScroll(startX, startY, dx, dy, mDuration);
}
}
}