国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁 > 系統 > Android > 正文

Android實現炫酷播放效果

2019-12-12 00:34:59
字體:
來源:轉載
供稿:網友

本文實例為大家分享了Android實現播放效果的具體代碼,供大家參考,具體內容如下

一、首先看效果

二、實現原理

使用貝塞爾曲線實現滑動效果,在使用屬性動畫實現水波紋效果,然后就能實現以上效果

三、實現

1、先封裝動畫框架,創建動畫基礎類

PathPoint.java

public class PathPoint {   public static final int MOVE = 0;  public static final int LINE = 1;  public static final int CURVE = 2;  float mControl0X, mControl0Y;  float mControl1X, mControl1Y;  public float mX, mY;  int mOperation;   //line/move  private PathPoint(int operation, float x, float y) {    this.mOperation = operation;    this.mX = x;    this.mY = y;  }   //curve  private PathPoint(float c0X, float c0Y, float c1X, float c1Y, float x, float y) {    this.mControl0X = c0X;    this.mControl0Y = c0Y;    this.mControl1X = c1X;    this.mControl1Y = c1Y;    this.mX = x;    this.mY = y;    this.mOperation = CURVE;   }   public static PathPoint moveTo(float x, float y) {     return new PathPoint(MOVE, x, y);   }   public static PathPoint lineTo(float x, float y) {     return new PathPoint(LINE, x, y);   }   public static PathPoint curveTo(float c0X, float c0Y, float c1X, float c1Y, float x, float y) {     return new PathPoint(c0X, c0Y, c1X, c1Y, x, y);   }}

2、創建動畫集合類,并且保存繪制軌跡

AnimatorPath

public class AnimatorPath {  //記錄軌跡  private List<PathPoint> mPoints = new ArrayList<>();   public void moveTo(float x, float y) {    mPoints.add(PathPoint.moveTo(x, y));  }   public void lineTo(float x, float y) {    mPoints.add(PathPoint.lineTo(x, y));  }   public void curveTo(float c0X, float c0Y, float c1X, float c1Y, float x, float y) {    mPoints.add(PathPoint.curveTo(c0X, c0Y, c1X, c1Y, x, y));  }    public Collection<PathPoint> getPoints() {    return mPoints;  }}

3、實現頁面布局

<?xml version="1.0" encoding="utf-8"?><RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"  xmlns:app="http://schemas.android.com/apk/res-auto"  android:layout_width="match_parent"  android:layout_height="match_parent"  android:background="#ffe8e8e8">    <ImageView    android:id="@+id/album_cover"    android:layout_width="match_parent"    android:layout_height="250dp"    android:background="#22eeff" />   <android.support.v7.widget.Toolbar    android:id="@+id/toolbar"    android:layout_width="match_parent"    android:layout_height="120dp"    android:layout_below="@id/album_cover"    android:layout_marginTop="-15dp"    android:background="@color/colorPrimary"    android:elevation="4dp"    android:minHeight="?attr/actionBarSize"    android:paddingLeft="72dp">     <LinearLayout      android:layout_width="wrap_content"      android:layout_height="wrap_content"      android:gravity="center_vertical"      android:orientation="vertical">       <TextView        android:layout_width="wrap_content"        android:layout_height="wrap_content"        android:fontFamily="sans-serif"        android:text="大海大海"        android:textColor="#FFF"        android:textSize="30sp" />      <TextView        android:layout_width="wrap_content"        android:layout_height="wrap_content"        android:layout_gravity="center_vertical"        android:fontFamily="sans-serif-light"        android:text="王小二"        android:textColor="#9cffffff"        android:textSize="18sp" />    </LinearLayout>  </android.support.v7.widget.Toolbar>   <FrameLayout    android:id="@+id/fab_container"    android:layout_width="match_parent"    android:layout_height="128dp"    android:layout_below="@id/album_cover"    android:layout_marginTop="-30dp"    android:elevation="10dp">     <LinearLayout      android:id="@+id/media_controls_container"      android:layout_width="wrap_content"      android:layout_height="wrap_content"      android:layout_gravity="center"      android:orientation="horizontal">       <ImageView        android:layout_width="20dp"        android:layout_height="20dp"        android:scaleX="0"        android:scaleY="0"        android:src="@mipmap/play" />       <ImageView        android:id="@+id/iv_pause_play"        android:layout_width="20dp"        android:layout_height="20dp"        android:layout_marginLeft="50dp"        android:layout_marginRight="50dp"        android:scaleX="0"        android:scaleY="0"        android:src="@mipmap/play" />       <ImageView        android:layout_width="20dp"        android:layout_height="20dp"        android:layout_marginRight="50dp"        android:scaleX="0"        android:scaleY="0"        android:src="@mipmap/play" />     </LinearLayout>     <ImageButton      android:id="@+id/fab"      android:layout_width="56dp"      android:layout_height="56dp"      android:layout_gravity="top|right"      android:layout_marginRight="72dp"      android:background="@drawable/ripple"      android:elevation="5dp"      android:onClick="onPabPressed"      android:transitionName="button_fab" />  </FrameLayout> </RelativeLayout>

4、獲取控件,并且設置點擊事件,設置一些動畫常量

private View mFab;  private FrameLayout mFabcontainer;  private LinearLayout mControlsContainer;   //從什么時候開始執行動畫  private static final float SCALE_FACTOR = 13f;  //持續時間  private static final long ANIMATION_DURATION = 300;  //貝塞爾曲線滑動到什么時候開始執行動畫  private static final float MINIMUN_X_DISTANCE = 200;  private boolean mRevealFlag;  private float mFabSize;

5、給mFab設置點擊事件

private void onFabPressed(View view) {    final float startX = mFab.getX();    //開始動畫    AnimatorPath path = new AnimatorPath();    path.moveTo(0, 0);    path.curveTo(-200, 200, -400, 100, -600, 50);//    path.lineTo(-600,50);     ObjectAnimator anim = ObjectAnimator.ofObject(this, "fabLoc",        new PathEvaluator(), path.getPoints().toArray());    anim.setInterpolator(new AccelerateInterpolator());//    anim.setRepeatCount(ValueAnimator.INFINITE);//    anim.setRepeatMode(ValueAnimator.REVERSE);    anim.setDuration(ANIMATION_DURATION);    anim.start();    anim.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {      @Override      public void onAnimationUpdate(ValueAnimator valueAnimator) {        //到了path路徑中的某個位置就是開始擴散動畫        if (Math.abs(startX - mFab.getX()) > MINIMUN_X_DISTANCE) {          if (!mRevealFlag) {            ImageButton fab = (ImageButton) mFab;            fab.setImageDrawable(new BitmapDrawable());            //看布局里邊的FabContainer要比toolbar背景高mFabSize/2(為了最初的半個fab效果)            mFabcontainer.setY(mFabcontainer.getY() + mFabSize / 2);            //fab放大動畫            mFab.animate()                .scaleXBy(SCALE_FACTOR)                .scaleYBy(SCALE_FACTOR)                .setListener(mEndRevealListener)                .setDuration(ANIMATION_DURATION);            mRevealFlag = true;          }        }      }    });  }   public void setFabLoc(PathPoint newLoc) {    mFab.setTranslationX(newLoc.mX);    if (mRevealFlag) {      //因為布局里邊的mFabcontainer要比toolbar背景高mFabSize/2,所以fab為了看起來平順,需要上移mFabSize/2      mFab.setTranslationY(newLoc.mY - (mFabSize / 2));    } else {      mFab.setTranslationY(newLoc.mY);    }   }   private AnimatorListenerAdapter mEndRevealListener = new AnimatorListenerAdapter() {    @Override    public void onAnimationEnd(Animator animation) {      super.onAnimationEnd(animation);      mFab.setVisibility(View.INVISIBLE);      mFabcontainer.setBackgroundColor(getResources().getColor(R.color.colorAccent));      //reveal動畫完畢后,接著每一個子控件都有個縮放動畫(依次順序出來)      for (int i = 0; i < mControlsContainer.getChildCount(); i++) {        View v = mControlsContainer.getChildAt(i);        ViewPropertyAnimator animate = v.animate()            .scaleX(1)            .scaleY(1)            .setDuration(ANIMATION_DURATION);        animate.setStartDelay(i * 50);        animate.start();      }    }  };

PathEvaluator

public class PathEvaluator implements TypeEvaluator<PathPoint> {  @Override  public PathPoint evaluate(float t, PathPoint startValue, PathPoint endValue) {    //t執行的百分比 (0~1)    float x, y;    if (endValue.mOperation == PathPoint.CURVE) {      //三階貝塞爾曲線 公式      float oneMinusT = 1 - t;      x = oneMinusT * oneMinusT * oneMinusT * startValue.mX +          3 * oneMinusT * oneMinusT * t * endValue.mControl0X +          3 * oneMinusT * t * t * endValue.mControl1X +          t * t * t * endValue.mX;      y = oneMinusT * oneMinusT * oneMinusT * startValue.mY +          3 * oneMinusT * oneMinusT * t * endValue.mControl0Y +          3 * oneMinusT * t * t * endValue.mControl1X +          t * t * t * endValue.mY;    } else if (endValue.mOperation == PathPoint.LINE) {      //x=起始點+t*起始點和終點的距離      x = startValue.mX + t * (endValue.mX - startValue.mX);      y = startValue.mY + t * (endValue.mY - startValue.mY);    } else {      x = endValue.mX;      y = endValue.mY;     }    return PathPoint.moveTo(x, y);  }}

注意:屬性動畫既可以改變屬性,也可以改變一個變量或者方法

以上就是本文的全部內容,希望對大家的學習有所幫助,也希望大家多多支持武林網。

發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
主站蜘蛛池模板: 云和县| 库车县| 衡山县| 靖宇县| 岳池县| 建阳市| 买车| 台东市| 韶关市| 清苑县| 西林县| 漳浦县| 湟中县| 南岸区| 营山县| 剑阁县| 合山市| 耒阳市| 塔河县| 城步| 绥阳县| 恭城| 东乡族自治县| 郧西县| 桃园县| 远安县| 墨竹工卡县| 吉林市| 吴堡县| 西青区| 南阳市| 江永县| 修水县| 武邑县| 奈曼旗| 三门峡市| 滦南县| 辽宁省| 徐州市| 祁连县| 军事|