仿 <赶集生活android客户端> 的介绍动画界面 的进一步修改

简介:

第一版项目引自

http://blog.csdn.net/nekocode/article/details/20308159#reply




        最近在玩赶集生活android客户端时,发现它初次运行时的介绍页面做得不错,当用户拉到Feature上的时候会出现动画,令人感觉很生动~于是自己简单地模仿了下。

        Sample: http://pan.baidu.com/s/1i3wqEMh (具体效果可以下载该样例观看)


 


  1. package com.example.animatetest;  
  2.   
  3. import android.os.Bundle;  
  4. import android.app.Activity;  
  5. import android.view.Menu;  
  6. import android.view.View;  
  7. import android.view.ViewTreeObserver.OnGlobalLayoutListener;  
  8. import android.view.animation.Animation;  
  9. import android.view.animation.AnimationUtils;  
  10.   
  11. public class MainActivity extends Activity implements OnGlobalLayoutListener, OnScrollChangedListener {  
  12.     private ObservableScrollView mScrollView;  
  13.     private View mAnimView;  
  14.     private int mScrollViewHeight;  
  15.     private int mStartAnimateTop;  
  16.       
  17.     @Override  
  18.     protected void onCreate(Bundle savedInstanceState) {  
  19.         super.onCreate(savedInstanceState);  
  20.         setContentView(R.layout.activity_main);  
  21.           
  22.         mScrollView = (ObservableScrollView)this.findViewById(R.id.scrollView1);  
  23.         mScrollView.getViewTreeObserver().addOnGlobalLayoutListener(this);  
  24.         mScrollView.setOnScrollChangedListener(this);  
  25.           
  26.         mAnimView = this.findViewById(R.id.anim1);  
  27.         mAnimView.setVisibility(View.INVISIBLE);  
  28.     }  
  29.   
  30.     @Override  
  31.     public boolean onCreateOptionsMenu(Menu menu) {  
  32.         getMenuInflater().inflate(R.menu.main, menu);  
  33.         return true;  
  34.     }  
  35.   
  36.     @Override  
  37.     public void onGlobalLayout() {  
  38.         mScrollViewHeight = mScrollView.getHeight();  
  39.         mStartAnimateTop = mScrollViewHeight / 3 * 2;  
  40.     }  
  41.   
  42.     boolean hasStart = false;  
  43.     @Override  
  44.     public void onScrollChanged(int top, int oldTop) {  
  45.         int animTop = mAnimView.getTop() - top;  
  46.           
  47.         if(top > oldTop) {  
  48.             if(animTop < mStartAnimateTop && !hasStart) {  
  49.                 Animation anim1 = AnimationUtils.loadAnimation(this, R.anim.feature_anim2scale_in);  
  50.                 anim1.setAnimationListener(new FeatureAnimationListener(mAnimView, true));  
  51.                   
  52.                 mAnimView.startAnimation(anim1);  
  53.                 hasStart = true;  
  54.             }  
  55.         } else {  
  56.             if(animTop > mStartAnimateTop && hasStart) {  
  57.                 Animation anim1 = AnimationUtils.loadAnimation(this, R.anim.feature_alpha_out);  
  58.                 anim1.setAnimationListener(new FeatureAnimationListener(mAnimView, false));  
  59.                   
  60.                 mAnimView.startAnimation(anim1);  
  61.                 hasStart = false;  
  62.             }  
  63.         }  
  64.     }  
  65. }  

  1. package com.example.animatetest;  
  2.   
  3. import android.content.Context;  
  4. import android.util.AttributeSet;  
  5. import android.widget.ScrollView;  
  6.   
  7. public class ObservableScrollView extends ScrollView {  
  8.     private OnScrollChangedListener onScrollChangedListener;  
  9.   
  10.     public ObservableScrollView(Context context, AttributeSet attrs,  
  11.             int defStyle) {  
  12.         super(context, attrs, defStyle);  
  13.     }  
  14.   
  15.     public ObservableScrollView(Context context, AttributeSet attrs) {  
  16.         super(context, attrs);  
  17.     }  
  18.   
  19.     public ObservableScrollView(Context context) {  
  20.         super(context);  
  21.     }  
  22.       
  23.     @Override  
  24.     protected void onScrollChanged(int l, int t, int oldl, int oldt) {  
  25.         super.onScrollChanged(l, t, oldl, oldt);  
  26.         if(this.onScrollChangedListener != null) {  
  27.             onScrollChangedListener.onScrollChanged(t, oldt);  
  28.         }  
  29.     }  
  30.   
  31.     public void setOnScrollChangedListener(OnScrollChangedListener onScrollChangedListener) {  
  32.         this.onScrollChangedListener = onScrollChangedListener;  
  33.     }  
  34.   
  35. }  

  1. package com.example.animatetest;  
  2.   
  3. public abstract interface OnScrollChangedListener {  
  4.     public abstract void onScrollChanged(int top, int oldTop);  
  5. }  

  1. package com.example.animatetest;  
  2.   
  3. import android.view.View;  
  4. import android.view.animation.Animation;  
  5. import android.view.animation.Animation.AnimationListener;  
  6.   
  7. public class FeatureAnimationListener implements AnimationListener {  
  8.     private View mAnimView;  
  9.     private boolean mAnimIn;  
  10.       
  11.     public FeatureAnimationListener(View animView, boolean animIn) {  
  12.         mAnimView = animView;  
  13.         mAnimIn = animIn;  
  14.     }  
  15.   
  16.     @Override  
  17.     public void onAnimationEnd(Animation animation) {  
  18.         if(!mAnimIn) {  
  19.             mAnimView.setVisibility(View.INVISIBLE);  
  20.         }  
  21.     }  
  22.   
  23.     @Override  
  24.     public void onAnimationRepeat(Animation animation) {}  
  25.   
  26.     @Override  
  27.     public void onAnimationStart(Animation animation) {  
  28.         if(mAnimIn) {  
  29.             mAnimView.setVisibility(View.VISIBLE);  
  30.         }  
  31.     }  
  32.   
  33. }  


activity_main.xml

  1. <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"  
  2.     xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent"  
  3.     android:layout_height="match_parent" tools:context=".MainActivity">  
  4.     <com.example.animatetest.ObservableScrollView  
  5.         android:id="@+id/scrollView1" android:layout_width="fill_parent"  
  6.         android:layout_height="fill_parent">  
  7.         <LinearLayout android:layout_width="fill_parent"  
  8.             android:layout_height="wrap_content" android:background="@drawable/feature_bg"  
  9.             android:gravity="center_horizontal" android:orientation="vertical">  
  10.             <ImageView android:id="@+id/imageView2"  
  11.                 android:layout_width="wrap_content" android:layout_height="wrap_content"  
  12.                 android:layout_marginTop="100dp" android:src="@drawable/feature_title" />  
  13.             <ImageView android:id="@+id/imageView1"  
  14.                 android:layout_width="wrap_content" android:layout_height="wrap_content"  
  15.                 android:layout_marginTop="20dp" android:src="@drawable/feature_lv" />  
  16.             <ImageView android:id="@+id/imageView3"  
  17.                 android:layout_width="wrap_content" android:layout_height="wrap_content"  
  18.                 android:layout_marginTop="35dp" android:src="@drawable/feature_dot" />  
  19.             <ImageView android:id="@+id/imageView4"  
  20.                 android:layout_width="wrap_content" android:layout_height="wrap_content"  
  21.                 android:layout_marginTop="35dp" android:src="@drawable/feature_dot" />  
  22.             <ImageView android:id="@+id/imageView5"  
  23.                 android:layout_width="wrap_content" android:layout_height="wrap_content"  
  24.                 android:layout_marginTop="35dp" android:src="@drawable/feature_scroll_txt" />  
  25.             <ImageView android:id="@+id/imageView6"  
  26.                 android:layout_width="wrap_content" android:layout_height="wrap_content"  
  27.                 android:layout_marginTop="35dp" android:src="@drawable/feature_dot" />  
  28.             <ImageView android:id="@+id/imageView7"  
  29.                 android:layout_width="wrap_content" android:layout_height="wrap_content"  
  30.                 android:layout_marginTop="35dp" android:src="@drawable/feature_dot" />  
  31.             <LinearLayout android:id="@+id/anim1"  
  32.                 android:layout_width="match_parent" android:layout_height="wrap_content"  
  33.                 android:layout_marginTop="35dp" android:gravity="center_vertical|center_horizontal">  
  34.                 <ImageView android:id="@+id/imageView8"  
  35.                     android:layout_width="wrap_content" android:layout_height="wrap_content"  
  36.                     android:src="@drawable/feature_car" />  
  37.                 <ImageView android:id="@+id/imageView9"  
  38.                     android:layout_width="wrap_content" android:layout_height="wrap_content"  
  39.                     android:src="@drawable/feature_gift" />  
  40.                 <ImageView android:id="@+id/imageView10"  
  41.                     android:layout_width="wrap_content" android:layout_height="wrap_content"  
  42.                     android:src="@drawable/feature_money" />  
  43.             </LinearLayout>  
  44.             <ImageView android:id="@+id/imageView11"  
  45.                 android:layout_width="wrap_content" android:layout_height="wrap_content"  
  46.                 android:layout_marginTop="35dp" android:src="@drawable/feature_dot" />  
  47.             <ImageView android:id="@+id/imageView12"  
  48.                 android:layout_width="wrap_content" android:layout_height="wrap_content"  
  49.                 android:layout_marginTop="35dp" android:src="@drawable/feature_dot" />  
  50.             <ImageView android:id="@+id/imageView13"  
  51.                 android:layout_width="wrap_content" android:layout_height="wrap_content"  
  52.                 android:layout_marginTop="35dp" android:src="@drawable/feature_arrow_up" />  
  53.             <ImageView android:id="@+id/imageView14"  
  54.                 android:layout_width="wrap_content" android:layout_height="wrap_content"  
  55.                 android:layout_marginTop="35dp" android:src="@drawable/feature_jobs_txt" />  
  56.         </LinearLayout>  
  57.     </com.example.animatetest.ObservableScrollView>  
  58.   
  59. </RelativeLayout>  


feature_anim2scale_in.xml
  1. <?xml version="1.0" encoding="utf-8"?>  
  2. <scale android:interpolator="@android:anim/overshoot_interpolator"  
  3.     android:duration="200" android:pivotX="50.0%" android:pivotY="50.0%"  
  4.     android:fillAfter="true" android:fromXScale="0.0" android:toXScale="1.0"  
  5.     android:fromYScale="0.0" android:toYScale="1.0"  
  6.     xmlns:android="http://schemas.android.com/apk/res/android" />  


feature_alpha_out.xml
  1. <?xml version="1.0" encoding="utf-8"?>  
  2. <set xmlns:android="http://schemas.android.com/apk/res/android">  
  3.     <alpha android:interpolator="@android:anim/overshoot_interpolator"  
  4.         android:duration="200" android:fromAlpha="1.0" android:toAlpha="0.0" />  
  5. </set> 



然后这个DEMO我本人发现如下可以修改的地方:

    这个最好activity不要实现OnScrollChangedListener
实现类单独写多个
这样就可以有不同的策略来实现change

就把acitivity里的实现OnScrollChangedListener的类抽出来写一个DefaultOnScrollChangedListener类,
activity里就定义一个OnScrollChangedListener变量
oncreate时赋值给他DefaultOnScrollChangedListener的实例
hasStart这样用有点扯

hasStart最好包在ScrollView里

修改的代码如下:

package com.example.animatetest;

import android.os.Bundle;
import android.app.Activity;
import android.view.Menu;
import android.view.View;
import android.view.ViewTreeObserver.OnGlobalLayoutListener;
import android.view.animation.Animation;
import android.view.animation.AnimationUtils;

public class MainActivity extends Activity implements OnGlobalLayoutListener {
	private ObservableScrollView mScrollView;
	private View mAnimView;
	private int mScrollViewHeight;
	private int mStartAnimateTop;
	
	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.activity_main);
		
		mScrollView = (ObservableScrollView)this.findViewById(R.id.scrollView1);
		mScrollView.getViewTreeObserver().addOnGlobalLayoutListener(this);
		
		DefaultOnScrollChangedListener listener = new DefaultOnScrollChangedListener();
		mScrollView.setOnScrollChangedListener(listener);
		
		mAnimView = this.findViewById(R.id.anim1);
		mAnimView.setVisibility(View.INVISIBLE);
	}

	@Override
	public boolean onCreateOptionsMenu(Menu menu) {
		getMenuInflater().inflate(R.menu.main, menu);
		return true;
	}

	@Override
	public void onGlobalLayout() {
		mScrollViewHeight = mScrollView.getHeight();
		mStartAnimateTop = mScrollViewHeight / 3 * 2;
	}

    public View getmAnimView() {
        return mAnimView;
    }

    public int getmStartAnimateTop() {
        return mStartAnimateTop;
    }	
}



package com.example.animatetest;

import android.app.Activity;
import android.content.Context;
import android.view.View;
import android.view.animation.Animation;
import android.view.animation.AnimationUtils;
import android.widget.ScrollView;

public class DefaultOnScrollChangedListener implements OnScrollChangedListener{
    private boolean hasStart = false;
    
    @Override
    public void onScrollChanged(Context context, int top, int oldTop) {
        View mAnimView =((MainActivity) context).getmAnimView();
        int mStartAnimateTop = ((MainActivity) context).getmStartAnimateTop();
        
        int animTop = mAnimView.getTop() - top;
        
        if(top > oldTop) {
            if(animTop < mStartAnimateTop && !hasStart) {
                Animation anim1 = AnimationUtils.loadAnimation(context, R.anim.feature_anim2scale_in);
                anim1.setAnimationListener(new FeatureAnimationListener(mAnimView, true));
                
                mAnimView.startAnimation(anim1);
                hasStart = true;
            }
        } else {
            if(animTop > mStartAnimateTop && hasStart) {
                Animation anim1 = AnimationUtils.loadAnimation(context, R.anim.feature_alpha_out);
                anim1.setAnimationListener(new FeatureAnimationListener(mAnimView, false));
                
                mAnimView.startAnimation(anim1);
                hasStart = false;
            }
        }
    }
}


package com.example.animatetest;

import android.view.View;
import android.view.animation.Animation;
import android.view.animation.Animation.AnimationListener;

public class FeatureAnimationListener implements AnimationListener {
	private View mAnimView;
	private boolean mAnimIn;
	
	public FeatureAnimationListener(View animView, boolean animIn) {
		mAnimView = animView;
		mAnimIn = animIn;
	}

	@Override
	public void onAnimationEnd(Animation animation) {
		if(!mAnimIn) {
			mAnimView.setVisibility(View.INVISIBLE);
		}
	}

	@Override
	public void onAnimationRepeat(Animation animation) {}

	@Override
	public void onAnimationStart(Animation animation) {
		if(mAnimIn) {
			mAnimView.setVisibility(View.VISIBLE);
		}
	}

}



package com.example.animatetest;

import android.app.Activity;
import android.content.Context;
import android.util.AttributeSet;
import android.widget.ScrollView;

public class ObservableScrollView extends ScrollView {
	private OnScrollChangedListener onScrollChangedListener;

	public ObservableScrollView(Context context, AttributeSet attrs,
			int defStyle) {
	    super(context, attrs, defStyle);
	    //this.context = context;
	}

	public ObservableScrollView(Context context, AttributeSet attrs) {
		super(context, attrs);
	}

	public ObservableScrollView(Context context) {
		super(context);
	}
	
    @Override
	protected void onScrollChanged(int l, int t, int oldl, int oldt) {
		super.onScrollChanged(l, t, oldl, oldt);
		if(this.onScrollChangedListener != null) {
			onScrollChangedListener.onScrollChanged(this.getContext(), t, oldt);
		}
	}

	public void setOnScrollChangedListener(OnScrollChangedListener onScrollChangedListener) {
		this.onScrollChangedListener = onScrollChangedListener;
	}

}



package com.example.animatetest;

import android.app.Activity;
import android.content.Context;
import android.widget.ScrollView;

public abstract interface OnScrollChangedListener {
	public abstract void onScrollChanged(Context context, int top, int oldTop);
}


源代码下载地址如下:

http://download.csdn.net/detail/opzoonzhuzhengke/6999895





目录
相关文章
|
3月前
|
存储 Shell Android开发
基于Android P,自定义Android开机动画的方法
本文详细介绍了基于Android P系统自定义开机动画的步骤,包括动画文件结构、脚本编写、ZIP打包方法以及如何将自定义动画集成到AOSP源码中。
68 2
基于Android P,自定义Android开机动画的方法
|
11天前
|
Android开发 UED
Android 中加载 Gif 动画
【10月更文挑战第20天】加载 Gif 动画是 Android 开发中的一项重要技能。通过使用第三方库或自定义实现,可以方便地在应用中展示生动的 Gif 动画。在实际应用中,需要根据具体情况进行合理选择和优化,以确保用户体验和性能的平衡。可以通过不断的实践和探索,进一步掌握在 Android 中加载 Gif 动画的技巧和方法,为开发高质量的 Android 应用提供支持。
|
30天前
|
XML 数据可视化 Android开发
Android应用界面
Android应用界面中的布局和控件使用,包括相对布局、线性布局、表格布局、帧布局、扁平化布局等,以及AdapterView及其子类如ListView的使用方法和Adapter接口的应用。
18 0
Android应用界面
|
6月前
|
XML API PHP
Android使用XML-RPC实现blog客户端
Android使用XML-RPC实现blog客户端
51 2
|
2月前
|
XML Android开发 UED
💥Android UI设计新风尚!掌握Material Design精髓,让你的界面颜值爆表!🎨
随着移动应用市场的蓬勃发展,用户对界面设计的要求日益提高。为此,掌握由Google推出的Material Design设计语言成为提升应用颜值和用户体验的关键。本文将带你深入了解Material Design的核心原则,如真实感、统一性和创新性,并通过丰富的组件库及示例代码,助你轻松打造美观且一致的应用界面。无论是色彩搭配还是动画效果,Material Design都能为你的Android应用增添无限魅力。
55 1
|
6月前
|
Android开发
Android WindowFeature小探究,Android客户端Web页面通用性能优化实践
Android WindowFeature小探究,Android客户端Web页面通用性能优化实践
|
6月前
|
Android开发
定制Android关机界面
定制Android关机界面
87 0
|
3月前
|
Android开发 iOS开发 C#
Xamarin.Forms:从零开始的快速入门指南——打造你的首个跨平台移动应用,轻松学会用C#和XAML构建iOS与Android通用界面的每一个步骤
【8月更文挑战第31天】Xamarin.Forms 是一个强大的框架,让开发者通过单一共享代码库构建跨平台移动应用,支持 iOS、Android 和 Windows。使用 C# 和 XAML,它简化了多平台开发流程并保持一致的用户体验。本指南通过创建一个简单的 “HelloXamarin” 应用演示了 Xamarin.Forms 的基本功能和工作原理。
74 0
|
4月前
|
XML Android开发 数据格式
Android 中如何设置activity的启动动画,让它像dialog一样从底部往上出来
在 Android 中实现 Activity 的对话框式过渡动画:从底部滑入与从顶部滑出。需定义两个 XML 动画文件 `activity_slide_in.xml` 和 `activity_slide_out.xml`,分别控制 Activity 的进入与退出动画。使用 `overridePendingTransition` 方法在启动 (`startActivity`) 或结束 (`finish`) Activity 时应用这些动画。为了使前 Activity 保持静止,可定义 `no_animation.xml` 并在启动新 Activity 时仅设置新 Activity 的进入动画。
84 12