• android3D动画,绕y轴旋转


    原文地址:http://blog.csdn.net/x_i_a_o_h_a_i/article/details/40449847

    其实网上的3D旋转的例子很多,在这里我只是想把其代码做一个解释。

    先上图:

    代码:

    TurnAroundActivity

    /**
     * 图片浏览器的主Activity。
     * 
     * @author guolin
     */
    public class TurnAroundActivity extends Activity {
    
    	/**
    	 * 根布局
    	 */
    	private RelativeLayout layout;
    
    	/**
    	 * 用于展示图片列表的ListView
    	 */
    	private ListView picListView;
    
    	/**
    	 * 翻转后的布局
    	 */
    	private LinearLayout picture;
    
    	/**
    	 * 图片列表的适配器
    	 */
    	private PictureAdapter adapter;
    
    	/**
    	 * 存放所有图片的集合
    	 */
    	private List<Picture> picList = new ArrayList<Picture>();
    
    	@Override
    	protected void onCreate(Bundle savedInstanceState) {
    		super.onCreate(savedInstanceState);
    		requestWindowFeature(Window.FEATURE_NO_TITLE);
    		setContentView(R.layout.activity_around);
    		// 对图片列表数据进行初始化操作
    		initPics();
    		layout = (RelativeLayout) findViewById(R.id.layout);
    		picListView = (ListView) findViewById(R.id.pic_list_view);
    		picture = (LinearLayout) findViewById(R.id.picture);
    		adapter = new PictureAdapter(this, 0, picList);
    		picListView.setAdapter(adapter);
    		picListView.setOnItemClickListener(new OnItemClickListener() {
    			@Override
    			public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
    				
    				// 获取布局的中心点位置,作为旋转的中心点
    				float centerX = layout.getWidth() / 2f;
    				float centerY = layout.getHeight() / 2f;
    				// 构建3D旋转动画对象,旋转角度为0到90度,这使得ListView将会从可见变为不可见
    				final Rotate3dAnimation rotation = new Rotate3dAnimation(0, 90, centerX, centerY,
    						310.0f, true);
    				// 动画持续时间500毫秒
    				rotation.setDuration(500);
    				// 动画完成后保持完成的状态
    				rotation.setFillAfter(true);
    				rotation.setInterpolator(new AccelerateInterpolator());
    				// 设置动画的监听器
    				rotation.setAnimationListener(new TurnToImageView());
    				layout.startAnimation(rotation);
    			}
    		});
    		picture.setOnClickListener(new OnClickListener() {
    			@Override
    			public void onClick(View v) {
    				// 获取布局的中心点位置,作为旋转的中心点
    				float centerX = layout.getWidth() / 2f;
    				float centerY = layout.getHeight() / 2f;
    				// 构建3D旋转动画对象,旋转角度为360到270度,这使得ImageView将会从可见变为不可见,并且旋转的方向是相反的
    				final Rotate3dAnimation rotation = new Rotate3dAnimation(360, 270, centerX,
    						centerY, 310.0f, true);
    				// 动画持续时间500毫秒
    				rotation.setDuration(500);
    				// 动画完成后保持完成的状态
    				rotation.setFillAfter(true);
    				rotation.setInterpolator(new AccelerateInterpolator());
    				// 设置动画的监听器
    				rotation.setAnimationListener(new TurnToListView());
    				layout.startAnimation(rotation);
    			}
    		});
    	}
    
    	/**
    	 * 初始化图片列表数据。
    	 */
    	private void initPics() {
    		Picture bird = new Picture("Bird", R.drawable.bird);
    		picList.add(bird);
    		Picture winter = new Picture("Winter", R.drawable.winter);
    		picList.add(winter);
    		Picture autumn = new Picture("Autumn", R.drawable.autumn);
    		picList.add(autumn);
    		Picture greatWall = new Picture("Great Wall", R.drawable.great_wall);
    		picList.add(greatWall);
    		Picture waterFall = new Picture("Water Fall", R.drawable.water_fall);
    		picList.add(waterFall);
    	}
    
    	/**
    	 * 注册在ListView点击动画中的动画监听器,用于完成ListView的后续动画。
    	 * 
    	 * @author guolin
    	 */
    	class TurnToImageView implements AnimationListener {
    
    		@Override
    		public void onAnimationStart(Animation animation) {
    		}
    
    		/**
    		 * 当ListView的动画完成后,还需要再启动ImageView的动画,让ImageView从不可见变为可见
    		 */
    		@Override
    		public void onAnimationEnd(Animation animation) {
    			// 获取布局的中心点位置,作为旋转的中心点
    			float centerX = layout.getWidth() / 2f;
    			float centerY = layout.getHeight() / 2f;
    			// 将ListView隐藏
    			picListView.setVisibility(View.GONE);
    			// 将ImageView显示
    			picture.setVisibility(View.VISIBLE);
    			picture.requestFocus();
    			// 构建3D旋转动画对象,旋转角度为270到360度,这使得ImageView将会从不可见变为可见
    			final Rotate3dAnimation rotation = new Rotate3dAnimation(270, 360, centerX, centerY,
    					310.0f, false);
    			// 动画持续时间500毫秒
    			rotation.setDuration(500);
    			// 动画完成后保持完成的状态
    			rotation.setFillAfter(true);
    			rotation.setInterpolator(new AccelerateInterpolator());
    			layout.startAnimation(rotation);
    		}
    
    		@Override
    		public void onAnimationRepeat(Animation animation) {
    		}
    
    	}
    
    	/**
    	 * 注册在ImageView点击动画中的动画监听器,用于完成ImageView的后续动画。
    	 * 
    	 * @author guolin
    	 */
    	class TurnToListView implements AnimationListener {
    
    		@Override
    		public void onAnimationStart(Animation animation) {
    		}
    
    		/**
    		 * 当ImageView的动画完成后,还需要再启动ListView的动画,让ListView从不可见变为可见
    		 */
    		@Override
    		public void onAnimationEnd(Animation animation) {
    			// 获取布局的中心点位置,作为旋转的中心点
    			float centerX = layout.getWidth() / 2f;
    			float centerY = layout.getHeight() / 2f;
    			// 将ImageView隐藏
    			picture.setVisibility(View.GONE);
    			// 将ListView显示
    			picListView.setVisibility(View.VISIBLE);
    			picListView.requestFocus();
    			// 构建3D旋转动画对象,旋转角度为90到0度,这使得ListView将会从不可见变为可见,从而回到原点
    			final Rotate3dAnimation rotation = new Rotate3dAnimation(90, 0, centerX, centerY,
    					310.0f, false);
    			// 动画持续时间500毫秒
    			rotation.setDuration(500);
    			// 动画完成后保持完成的状态
    			rotation.setFillAfter(true);
    			rotation.setInterpolator(new AccelerateInterpolator());
    			layout.startAnimation(rotation);
    		}
    
    		@Override
    		public void onAnimationRepeat(Animation animation) {
    		}
    
    	}
    
    }


    关键类:

    Rotate3dAnimation
    /**
     * An animation that rotates the view on the Y axis between two specified
     * angles. This animation also adds a translation on the Z axis (depth) to
     * improve the effect.
     */
    public class Rotate3dAnimation extends Animation {
    	private final float mFromDegrees;
    	private final float mToDegrees;
    	private final float mCenterX;
    	private final float mCenterY;
    	private final float mDepthZ;
    	private final boolean mReverse;
    	private Camera mCamera;
    
    	/**
    	 * Creates a new 3D rotation on the Y axis. The rotation is defined by its
    	 * start angle and its end angle. Both angles are in degrees. The rotation
    	 * is performed around a center point on the 2D space, definied by a pair of
    	 * X and Y coordinates, called centerX and centerY. When the animation
    	 * starts, a translation on the Z axis (depth) is performed. The length of
    	 * the translation can be specified, as well as whether the translation
    	 * should be reversed in time.
    	 * 
    	 * @param fromDegrees
    	 *            the start angle of the 3D rotation
    	 * @param toDegrees
    	 *            the end angle of the 3D rotation
    	 * @param centerX
    	 *            the X center of the 3D rotation
    	 * @param centerY
    	 *            the Y center of the 3D rotation
    	 * @param reverse
    	 *            true if the translation should be reversed, false otherwise
    	 */
    	public Rotate3dAnimation(float fromDegrees, float toDegrees, float centerX, float centerY,
    			float depthZ, boolean reverse) {
    		mFromDegrees = fromDegrees;
    		mToDegrees = toDegrees;
    		mCenterX = centerX;
    		mCenterY = centerY;
    		mDepthZ = depthZ;
    		mReverse = reverse;
    	}
    
    	@Override
    	public void initialize(int width, int height, int parentWidth, int parentHeight) {
    		super.initialize(width, height, parentWidth, parentHeight);
    		mCamera = new Camera();
    	}
    
    	@Override
    	protected void applyTransformation(float interpolatedTime, Transformation t) {
    		final float fromDegrees = mFromDegrees;
    		float degrees = fromDegrees + ((mToDegrees - fromDegrees) * interpolatedTime);
    		final float centerX = mCenterX;
    		final float centerY = mCenterY;
    		final Camera camera = mCamera;
    		final Matrix matrix = t.getMatrix();
    		camera.save();
    		//z轴上的景深
    		if (mReverse) {
    			camera.translate(0.0f, 0.0f, mDepthZ * interpolatedTime);
    		} else {
    			camera.translate(0.0f, 0.0f, mDepthZ * (1.0f - interpolatedTime));
    		}
    		camera.rotateY(degrees);
    		camera.getMatrix(matrix);
    		camera.restore();
    		//camera.rotateY(degrees);其实围绕y轴旋转的坐标点是在(0,0);
    		//为了让其在围绕(centerX, centerY)点
    		//preTranslate 作用为在rotateY开始之前先把坐标(centerX, centerY)移到中心点
    		matrix.preTranslate(-centerX, -centerY);
    		//postTranslate 当执行完rotateY后再把中心点移动回来
    		matrix.postTranslate(centerX, centerY);
    	}
    }


    layout文件:

    <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
        android:id="@+id/layout"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
         >
    
        <ListView
            android:id="@+id/pic_list_view"
            android:layout_width="match_parent"
            android:layout_height="match_parent" 
            >
        </ListView>
        
        <LinearLayout 
            android:id="@+id/picture"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:clickable="true"
            android:orientation="vertical"
            android:visibility="gone"
            >
            <TextView
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:id="@+id/text"
                android:text="ddddddd"/>
            <ImageView 
                android:layout_width="200dp"
                android:layout_height="200dp"
                android:src="@drawable/bird"
                />
            <Button android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="ddddddd"/>
            
        </LinearLayout>
    
    </RelativeLayout>
  • 相关阅读:
    BZOJ2821 作诗(Poetize) 【分块】
    BZOJ2724 蒲公英 【分块】
    Codeforces 17E Palisection 【Manacher】
    BZOJ2565 最长双回文串 【Manacher】
    Codeforces 25E Test 【Hash】
    CODEVS3013 单词背诵 【Hash】【MAP】
    HDU2825 Wireless Password 【AC自动机】【状压DP】
    HDU2896 病毒侵袭 【AC自动机】
    HDU3065 病毒侵袭持续中【AC自动机】
    HDU2222 Keywords Search 【AC自动机】
  • 原文地址:https://www.cnblogs.com/BlogCommunicator/p/4976686.html
Copyright © 2020-2023  润新知