(使用格式工厂将视频转换成gif格式时影响了gif效果,运行在真机上不影响效果)
这个效果是采用ListView并给ListView添加一个头部来实现的,当然了要处理ListView的上拉,下拉及松开肯定要对ListView自定义;
先来看下ListView的头部xml文件:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent">
<ImageView
android:id="@+id/layout_header_image"
android:layout_width="match_parent"
android:layout_height="@dimen/size_default_height"
android:scaleType="centerCrop"
android:src="@drawable/image_header4"/>
<ImageView
android:id="@+id/header_iamge"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:src="@drawable/header"
android:layout_alignParentBottom="true"
android:layout_marginBottom="40dp"
android:layout_alignParentLeft="true"
android:layout_marginLeft="40dp"/>
</RelativeLayout>
很简单就是两个ImageView,不过需要设置背景ImageView的scaleType属性值为centerCrop(均衡的缩放图像(保持图像原始比例),使图片的两个坐标(宽、高)都大于等于 相应的视图坐标(负的内边距),图像则位于视图的中央),这样头部背景在ListView下拉、上拉及手势松开是能进行均衡的缩放效果;
接着动作就是自定义ListView:
public class ParallaxListView extends ListView {
private ImageView mImageView;
private ImageView headerImageView;
private int mImageViewHeight = 0;
public ParallaxListView(Context context) {
this(context, null);
}
public ParallaxListView(Context context, AttributeSet attrs) {
this(context, attrs, 0);
}
public ParallaxListView(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
mImageViewHeight = context.getResources().getDimensionPixelSize(R.dimen.size_default_height);
}
public void setZoomImageView(ImageView iv) {
this.mImageView = iv;
}
public void setHeaderImageView(ImageView iv){
this.headerImageView=iv;
}
@Override
protected boolean overScrollBy(int deltaX, int deltaY, int scrollX, int scrollY, int scrollRangeX, int scrollRangeY, int maxOverScrollX, int maxOverScrollY, boolean isTouchEvent) {
/**
* 监听ListView(ScrollView)的滑动过度
* dx,dy增量deltaY
* -:下拉过度
* +:上拉过度
*/
if (deltaY < 0) {
//放大 对ImageView的高度重新赋值
mImageView.getLayoutParams().height = mImageView.getHeight() - deltaY;
mImageView.requestLayout();
//旋转
// headerImageView.setRotation(headerImageView.getRotation()-deltaY);
} else {
//缩小对ImageView的高度重新赋值
if (mImageView.getHeight() > mImageViewHeight) {
mImageView.getLayoutParams().height = mImageView.getHeight() - deltaY;
mImageView.requestLayout();
}
}
return super.overScrollBy(deltaX, deltaY, scrollX, scrollY, scrollRangeX, scrollRangeY, maxOverScrollX, maxOverScrollY, isTouchEvent);
}
@Override
protected void onScrollChanged(int l, int t, int oldl, int oldt) {
//让ImageView在上滑时缩小,监听
View header = (View) mImageView.getParent();
//header.getTop() 头部滑出去的距离
if (header.getTop() < 0 && mImageView.getHeight() > mImageViewHeight) {
mImageView.getLayoutParams().height = mImageView.getHeight() + header.getTop();
header.layout(header.getLeft(), 0, header.getRight(), header.getBottom());
mImageView.requestLayout();
}
super.onScrollChanged(l, t, oldl, oldt);
}
@Override
public boolean onTouchEvent(MotionEvent ev) {
//监听松开手 弹回原来的状态
int action = ev.getAction();
if(action==MotionEvent.ACTION_UP){
//给ImagView设置动画效果
ResetAnimation animation=new ResetAnimation(mImageView,mImageViewHeight);
animation.setDuration(300);
mImageView.startAnimation(animation);
}
return super.onTouchEvent(ev);
}
/**
* 自定义动画
*/
public class ResetAnimation extends Animation{
private ImageView iv;
private int targetHeight;
private int originalHeight;
private int extraHeight;
public ResetAnimation(ImageView iv,int targetHeight){
this.iv=iv;
//最终恢复的高度
this.targetHeight=targetHeight;
//现在的高度
this.originalHeight=iv.getHeight();
this.extraHeight=originalHeight-targetHeight;
}
@Override
protected void applyTransformation(float interpolatedTime, Transformation t) {
//interpolatedTime (0.0 to 1.0)执行的百分比
iv.getLayoutParams().height = (int) (originalHeight-extraHeight*interpolatedTime);
iv.requestLayout();
super.applyTransformation(interpolatedTime, t);
}
}
}
在ParallaxListView里面需要重写三个方法:
overScrollBy();-->ListView、ScrollView等上拉或下拉滑动过度时回调;
onScrollChanged;-->ListView、ScrollView等滑动时回调;
onTouchEvent();-->ListView、ScrollView等手势触摸或松开时回调;
activity及xml布局文件中引用和使用:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/activity_main"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context="com.qqheader.MainActivity">
<com.qqheader.ParallaxListView
android:id="@+id/listview"
android:layout_width="match_parent"
android:layout_height="match_parent" />
</RelativeLayout>
public class MainActivity extends AppCompatActivity {
private ParallaxListView listview;
private List<String> list = new ArrayList<>();
private ListAdapter adapter;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
getData();
listview = (ParallaxListView) findViewById(R.id.listview);
View headerView=View.inflate(this,R.layout.listview_header,null);
ImageView iv = (ImageView) headerView.findViewById(R.id.layout_header_image);
ImageView headerIamge= (ImageView) headerView.findViewById(R.id.header_iamge);
adapter = new ListAdapter(this, list);
listview.addHeaderView(headerView);
listview.setAdapter(adapter);
listview.setZoomImageView(iv);
listview.setOnItemClickListener(new AdapterView.OnItemClickListener() {
@Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
Toast.makeText(MainActivity.this,list.get(position-1),Toast.LENGTH_LONG).show();
}
});
}
private void getData() {
list.add("星期一");
list.add("星期二");
list.add("星期三");
list.add("星期四");
list.add("星期五");
list.add("星期六");
list.add("星期日");
list.add("星期一");
list.add("星期二");
list.add("星期三");
list.add("星期四");
list.add("星期五");
list.add("星期六");
list.add("星期日");
}
}