1、首先需要自定义scrollview,解决scrollview嵌套viewpager,导致viewpage无法滑动问题
/**
* 自定义ScrollView,解决:ScrollView嵌套ViewPager,导致ViewPager不能滑动的问题
*/
public class CustomScrollView extends ScrollView {
private GestureDetector mGestureDetector;
private int Scroll_height = 0;
private int view_height = 0;
protected Field scrollView_mScroller;
private static final String TAG = "CustomScrollView";
public CustomScrollView(Context context, AttributeSet attrs) {
super(context, attrs);
mGestureDetector = new GestureDetector(context, new YScrollDetector());
setFadingEdgeLength(0);
}
@Override
public boolean onInterceptTouchEvent(MotionEvent ev) {
if (ev.getAction() == MotionEvent.ACTION_DOWN) {
stopAnim();
}
boolean ret = super.onInterceptTouchEvent(ev);
boolean ret2 = mGestureDetector.onTouchEvent(ev);
return ret && ret2;
}
// Return false if we're scrolling in the x direction
class YScrollDetector extends SimpleOnGestureListener {
@Override
public boolean onScroll(MotionEvent e1, MotionEvent e2,
float distanceX, float distanceY) {
if (Math.abs(distanceY) > Math.abs(distanceX)) {
return true;
}
return false;
}
}
@Override
protected void onScrollChanged(int l, int t, int oldl, int oldt) {
boolean stop = false;
if (Scroll_height - view_height == t) {
stop = true;
}
if (t == 0 || stop == true) {
try {
if (scrollView_mScroller == null) {
scrollView_mScroller = getDeclaredField(this, "mScroller");
}
Object ob = scrollView_mScroller.get(this);
if (ob == null || !(ob instanceof Scroller)) {
return;
}
Scroller sc = (Scroller) ob;
sc.abortAnimation();
} catch (Exception e) {
Log.e(TAG, e.getMessage());
}
}
super.onScrollChanged(l, t, oldl, oldt);
}
private void stopAnim() {
try {
if (scrollView_mScroller == null) {
scrollView_mScroller = getDeclaredField(this, "mScroller");
}
Object ob = scrollView_mScroller.get(this);
if (ob == null) {
return;
}
Method method = ob.getClass().getMethod("abortAnimation");
method.invoke(ob);
} catch (Exception ex) {
Log.e(TAG, ex.getMessage());
}
}
@Override
protected int computeVerticalScrollRange() {
Scroll_height = super.computeVerticalScrollRange();
return Scroll_height;
}
@Override
protected void onLayout(boolean changed, int l, int t, int r, int b) {
super.onLayout(changed, l, t, r, b);
if (changed == true) {
view_height = b - t;
}
}
@Override
public void requestChildFocus(View child, View focused) {
if (focused != null && focused instanceof WebView) {
return;
}
super.requestChildFocus(child, focused);
}
/**
* 获取一个对象隐藏的属性,并设置属性为public属性允许直接访问
*
* @return {@link Field} 如果无法读取,返回null;返回的Field需要使用者自己缓存,本方法不做缓存�?
*/
public static Field getDeclaredField(Object object, String field_name) {
Class<?> cla = object.getClass();
Field field = null;
for (; cla != Object.class; cla = cla.getSuperclass()) {
try {
field = cla.getDeclaredField(field_name);
field.setAccessible(true);
return field;
} catch (Exception e) {
}
}
return null;
}
}
2、接下来有两种改变高度的方法
方法1:生硬变化,就是没有过渡效果,比较死板,方法也比较简单
//在oncreate中直接给viewPager添加setOnPageChangeListener
oncreate{
viewPager.setOnPageChangeListener(new MyListener());
//初始化的时候执行
new myAsyncTask().execute();
}
public class MyListener implements ViewPager.OnPageChangeListener {
@Override
public void onPageScrollStateChanged(int arg0) {
}
@Override
public void onPageScrolled(int position, float positionOffset,
int positionOffsetPixels) {
Log.i("zjz","positionOffset="+positionOffset+"positionOffsetPixels="+positionOffsetPixels);
}
@Override
public void onPageSelected(int position) {
// 页面切换后重置ViewPager高度
resetViewPagerHeight(position);
}
}
public void resetViewPagerHeight(int position) {
View child = viewPager.getChildAt(position);
if (child != null) {
child.measure(0, 0);
int h = child.getMeasuredHeight();
RelativeLayout.LayoutParams params = (RelativeLayout.LayoutParams) viewPager.getLayoutParams();
params.height = h ;
viewPager.setLayoutParams(params);
}
}
public class myAsyncTask extends AsyncTask<Void, Void, Void> {
@Override
protected Void doInBackground(Void... params) {
try {
Thread.sleep(500);
} catch (InterruptedException e) {
e.printStackTrace();
}
return null;
}
@Override
protected void onPostExecute(Void result) {
resetViewPagerHeight(0);
}
}
方法2:滑动过程中带有动画过渡效果
//图片数组
private ArrayList<Integer>images=new ArrayList<>();
//各个图片高度数组
private int[] heights;
images.add(R.drawable.img_main_banner1);
images.add(R.drawable.img_service_test1);
heights=new int[images.size()];
viewPager.setOnPageChangeListener(new MyListener());
viewPager.getViewTreeObserver().addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
@Override
public void onGlobalLayout() {
//初始化各个页面
for (int i = 0;i<images.size();i++){
ImageView imageView = new ImageView(ShareDetailActivity.this);
Drawable iconDrawable = getResources().getDrawable(images.get(i));
//计算该页面合适的高度,使得图片完整的显示,填充整个高度和宽度
heights[i] = (int) (viewPager.getWidth()/(float)iconDrawable.getIntrinsicWidth()*iconDrawable.getIntrinsicHeight());
imageView.setImageDrawable(iconDrawable);
// imageViews.add(imageView);
}
pagerAdapter.notifyDataSetChanged();
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
viewPager.getViewTreeObserver().removeOnGlobalLayoutListener(this);
} else {
viewPager.getViewTreeObserver().removeGlobalOnLayoutListener(this);
}
//ViewPager的初始高度设置为第一个页面的高度
ViewGroup.LayoutParams layoutParams = viewPager.getLayoutParams();
layoutParams.height = heights[0];
viewPager.setLayoutParams(layoutParams);
}
});
public class MyListener implements ViewPager.OnPageChangeListener {
@Override
public void onPageScrollStateChanged(int arg0) {
}
@Override
public void onPageScrolled(int position, float positionOffset,
int positionOffsetPixels) {
Log.i("zjz","positionOffset="+positionOffset+"positionOffsetPixels="+positionOffsetPixels);
if (position==heights.length-1){
return;
}
//计算ViewPager现在应该的高度,heights[]表示页面高度的数组。
int height = (int) (heights[position]*(1-positionOffset)+heights[position+1]*positionOffset);
//为ViewPager设置高度
ViewGroup.LayoutParams params = viewPager.getLayoutParams();
params.height = height;
viewPager.setLayoutParams(params);
}
@Override
public void onPageSelected(int position) {
}
}