类似滑动控件ScrollView、ListView、ViewPager等控件,当滑动到最顶部或者最底部,再继续滑动的时候,会出现阴影,个人感觉这个阴影不是很好看,有点影响用户体验,那么我们如何去掉这个阴影呢?其实很简单,我们只需要设置android:overScrollMode="never"或在代码中setOverScrollMode(View.OVER_SCROLL_NEVER),这样就可以去掉阴影。
本文当然不只简单的教大家如何去掉阴影,而是带给大家一种解决问题的思路,很多人遇到问题都喜欢百度或谷歌,我个人比较喜欢从源码的角度去分析,下面我就带着大家看一下ScrollView中是如何绘制这个阴影的,其他滑动控件类似,这里不再重复,首先进入ScrollView,按照Android view的绘制原理,这个阴影肯定是在draw()方法里面绘制,那么我们就直接看下它的draw()方法,源码如下:
@Override
public void draw(Canvas canvas) {
super.draw(canvas);
//如果顶部的阴影效果不等于null,则绘制阴影
if (mEdgeGlowTop != null) {
final int scrollY = mScrollY;
//顶部阴影效果
if (!mEdgeGlowTop.isFinished()) {
final int restoreCount = canvas.save();
final int width = getWidth() - mPaddingLeft - mPaddingRight;
canvas.translate(mPaddingLeft, Math.min(0, scrollY));
mEdgeGlowTop.setSize(width, getHeight());
//绘制顶部阴影
if (mEdgeGlowTop.draw(canvas)) {
postInvalidateOnAnimation();
}
canvas.restoreToCount(restoreCount);
}
//底部的阴影效果
if (!mEdgeGlowBottom.isFinished()) {
final int restoreCount = canvas.save();
final int width = getWidth() - mPaddingLeft - mPaddingRight;
final int height = getHeight();
canvas.translate(-width + mPaddingLeft,
Math.max(getScrollRange(), scrollY) + height);
canvas.rotate(180, width, 0);
mEdgeGlowBottom.setSize(width, height);
//绘制底部阴影
if (mEdgeGlowBottom.draw(canvas)) {
postInvalidateOnAnimation();
}
canvas.restoreToCount(restoreCount);
}
}
}
在draw()方法里面有个mEdgeGlowTop对象,当这个对象不会null时,则绘制该对象,咦,难道这就是阴影效果,再一看它的类型EdgeEffect ,边界效果,恩,大概就是这个了吧,那么如何让它为null呢,于是我们就看一下该对象在类中的引用情况,发现它是在setOverScrollModel中初始化的,源码如下:
@Override
public void setOverScrollMode(int mode) {
if (mode != OVER_SCROLL_NEVER) {
if (mEdgeGlowTop == null) {
Context context = getContext();
mEdgeGlowTop = new EdgeEffect(context);
mEdgeGlowBottom = new EdgeEffect(context);
}
} else {
//当mode==OVER_SCROLL_NEVER时,不初始化对象
mEdgeGlowTop = null;
mEdgeGlowBottom = null;
}
super.setOverScrollMode(mode);
}
}
很明显,如果想让顶部和底部的EdgeEffect对象为null,则mode必须为OVER_SCROLL_NEVER,xml中的配置为:android:overScrollMode="never"。测试后,发现阴影确实没了,爽歪歪有没有!其他控件也是类似的,比如ListView->AbsListView中的draw(),HorizontalScrollView中的draw()。