1.ScrollView中嵌套ScrollView而且内部ScrollView也可滑动
(1)ScrollView继承类
public class InnerScrollView extends ScrollView { Handler handler; public ScrollView parentScrollView; public InnerScrollView(Context context, AttributeSet attrs) {
super(context, attrs);
handler = new Handler(); } private int lastScrollDelta = 0; public void resume() {
overScrollBy(0, -lastScrollDelta, 0, getScrollY(), 0, getScrollRange(), 0, 0, true);
lastScrollDelta = 0;
} int mTop = 10; /**
* 将targetView滚到最顶端
*/
public void scrollTo(final View targetView) { handler.postDelayed(new Runnable() { @Override
public void run() {
int oldScrollY = getScrollY();
int top = targetView.getTop() - mTop;
final int delatY = top - oldScrollY;
lastScrollDelta = delatY;
smoothScrollTo(0, top);
}
}, 50); } private int getScrollRange() {
int scrollRange = 0;
if (getChildCount() > 0) {
View child = getChildAt(0);
scrollRange = Math.max(0, child.getHeight() - (getHeight()));
}
return scrollRange;
} int currentY; @Override
public boolean onInterceptTouchEvent(MotionEvent ev) {
if (parentScrollView == null) {
return super.onInterceptTouchEvent(ev);
} else {
if (ev.getAction() == MotionEvent.ACTION_DOWN) {
// 将父scrollview的滚动事件拦截
currentY = (int)ev.getY();
setParentScrollAble(false);
return super.onInterceptTouchEvent(ev);
} else if (ev.getAction() == MotionEvent.ACTION_UP) {
// 把滚动事件恢复给父Scrollview
setParentScrollAble(true);
} else if (ev.getAction() == MotionEvent.ACTION_MOVE) {
}
}
return super.onInterceptTouchEvent(ev); } @Override
public boolean onTouchEvent(MotionEvent ev) {
View child = getChildAt(0);
if (parentScrollView != null) {
if (ev.getAction() == MotionEvent.ACTION_MOVE) {
int height = child.getMeasuredHeight();
height = height - getMeasuredHeight(); // System.out.println("height=" + height);
int scrollY = getScrollY();
// System.out.println("scrollY" + scrollY);
int y = (int)ev.getY(); // 手指向下滑动
if (currentY < y) {
if (scrollY <= 0) {
// 假设向下滑动到头。就把滚动交给父Scrollview
setParentScrollAble(true);
return false;
} else {
setParentScrollAble(false); }
} else if (currentY > y) {
if (scrollY >= height) {
// 假设向上滑动到头,就把滚动交给父Scrollview
setParentScrollAble(true);
return false;
} else {
setParentScrollAble(false); } }
currentY = y;
}
} return super.onTouchEvent(ev);
} /**
* 是否把滚动事件交给父scrollview
*
* @param flag
*/
private void setParentScrollAble(boolean flag) { parentScrollView.requestDisallowInterceptTouchEvent(!flag);
}
}
(2)ScrollView使用Activity
public class ScrollViewActivity extends Activity { ScrollView scrollView1; InnerScrollView innerScrollView; @Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
scrollView1 = (ScrollView)findViewById(R.id.scroll_1);
innerScrollView = (InnerScrollView)findViewById(R.id.scroll_2);
innerScrollView.parentScrollView = scrollView1;
final Button button = (Button)innerScrollView.findViewById(R.id.scroll_button2);
final View content = findViewById(R.id.scroll_content);
button.setOnClickListener(new OnClickListener() { @Override
public void onClick(View v) { if (content.getVisibility() == View.VISIBLE) {
innerScrollView.resume();
content.setVisibility(View.GONE);
} else {
innerScrollView.scrollTo(v);
content.setVisibility(View.VISIBLE);
}
}
}); }
}
2.ScrollView中嵌套ListView而且内部ListView也可滑动
(1)ScrollView继承类
public class InnerListView extends ListView { ScrollView parentScrollView; public ScrollView getParentScrollView() {
return parentScrollView;
} public void setParentScrollView(ScrollView parentScrollView) {
this.parentScrollView = parentScrollView;
} private int maxHeight; public int getMaxHeight() {
return maxHeight;
} public void setMaxHeight(int maxHeight) {
this.maxHeight = maxHeight;
} public InnerListView(Context context, AttributeSet attrs) {
super(context, attrs);
} @Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
// TODO Auto-generated method stub if (maxHeight > -1) { heightMeasureSpec = MeasureSpec.makeMeasureSpec(maxHeight, MeasureSpec.AT_MOST); } super.onMeasure(widthMeasureSpec, heightMeasureSpec);
System.out.println(getChildAt(0));
} @Override
public boolean onInterceptTouchEvent(MotionEvent ev) { switch (ev.getAction()) {
case MotionEvent.ACTION_DOWN: setParentScrollAble(false);
case MotionEvent.ACTION_MOVE: break;
case MotionEvent.ACTION_UP: case MotionEvent.ACTION_CANCEL:
setParentScrollAble(true);
break;
default:
break;
}
return super.onInterceptTouchEvent(ev);
} /**
* @param flag
*/
private void setParentScrollAble(boolean flag) {
parentScrollView.requestDisallowInterceptTouchEvent(!flag);
} }
(2)ScrollView有用Activity
public class ListViewActivity extends Activity { ScrollView scrollView; InnerListView listView; @Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.list_view_test);
listView = (InnerListView)findViewById(R.id.list);
scrollView = (ScrollView)findViewById(R.id.scroll_view); ArrayAdapter<String> adapter = new ArrayAdapter<String>(this,
android.R.layout.select_dialog_singlechoice);
for (int i = 0; i < 100; i++) {
adapter.add(String.valueOf(i));
}
listView.setAdapter(adapter);
listView.setCacheColorHint(0x00000000);
listView.setBackgroundDrawable(null);
listView.setBackgroundColor(Color.WHITE);
listView.setParentScrollView(scrollView);
listView.setMaxHeight(400); }
}