Android教程網
  1. 首頁
  2. Android 技術
  3. Android 手機
  4. Android 系統教程
  5. Android 游戲
 Android教程網 >> Android技術 >> 關於Android編程 >> Android群英傳筆記——第十二章:Android5.X 新特性詳解,Material Design UI的新體驗

Android群英傳筆記——第十二章:Android5.X 新特性詳解,Material Design UI的新體驗

編輯:關於Android編程

這一章很多,但是很有趣,也是這書的最後一章知識點了,我現在還在考慮要不要寫這個拼圖和2048的案例,在此之前,我們先來玩玩Android5.X的新特性吧!

Android 5.X UI設計初步 Android 5.X 新增特性分析

一. Android 5.X UI設計初步

Android 5.X開始使用新的設計風格Material Design來統一整個Android系統設計風格,與之前的設計不同,這次的Material Design設計將Android帶來一片全新的高度,同時Google在官網推出了新的設計指南,全面的講解了Material Design的整個實現規范

這裡寫圖片描述

1.材料的形態模擬

材料的形態模擬是Material Design中最核心也是改變最大的設計,Google通過模擬自然界紙墨的形態變化,光線和陰影,紙和紙之間的空間層次關系,帶來一種真實的感覺

這裡寫圖片描述

2.更加真實的動畫

好的動畫效果可以非常的有效的指引用戶,暗示用戶並給用戶帶來愉悅的使用體驗,Android5.X中大量加入了各種新的動畫效果,讓整個設計風格更加自然,和諧,而各種新的轉場動畫,能更加有效的指引用戶的視覺焦點,不至於因為復雜布局的界面重排而對整體效果產生影響,讓使用者達到一個視覺連貫性

這裡寫圖片描述

3.大色塊的使用

Material Design中用了大量高飽和度,適中亮度的大色塊來突出界面的主次,並一掃Android4.X系列Holo主題的沉重感,讓界面更加富有時尚感和視覺沖擊力

這裡寫圖片描述

此外,還有更多的設計風格,比如懸浮按鈕,聚焦大圖,無框按鈕,波紋效果等新特性,這裡就不一一列舉了,Google在其Material Design網站上也有

2.Material Design主題

我們先來看看如何使用主題,MD一共有三種默認的主題可以設置

@android:style/Theme.Material (dark version)        
@android:style/Theme.Material.Light (light version)     
@android:style/Theme.Material.Light.DarkActionBar   

效果如圖

這裡寫圖片描述

同時,Android5.X提出來Color Palette的概念,讓開發者可以設定系統區域的顏色,使得整個APP的顏色使得APP的顏色統一

這裡寫圖片描述

通過如下所示的代碼,可以通過自定義style的方式來創建自己的ColZ喎?/kf/ware/vc/" target="_blank" class="keylink">vciBwYWxldHRl0dXJq9b3zOKjrLTTtvjKtc/W0dXJq7XEsrvNrLfnuPE8L3A+DQo8L2Jsb2NrcXVvdGU+DQo8cHJlIGNsYXNzPQ=="brush:java;">

看效果

這裡寫圖片描述

3.Palette

在Android的版本發展中,UI越來越成為Google的發展中心,這次的Android5.X創新的使用了Palette來提取顏色,從而讓主題能夠動態適應當前頁面的色調,使得整個app的顏色基本和諧統一

Android內置了幾種提取顏色的種類

Vibrant(充滿活力的) Vibrant dark(充滿活力的黑) Vibrant light(充滿活力的白) Muted(柔和的) Muted dark(柔和的黑) Muted light(柔和的白)

使用Palette的API,能夠讓我們從Bitmap中獲取對應的色調,修改當前的主題色調,使用Palette首先需要在Android studio引用相關的依賴

compile 'com.android.support:palette-v7:21.0.+'

可以通過傳遞一個Bitmap對象給Palette,並調用它的Palette.generate()靜態方法或者Palette.generateAsync()方法創建一個Palette,接下來,就可以使用getter方法來檢索相應的色調,這些色調就是我們在上面列表所列出的色調

我們這裡寫一個小例子,演示如何通過加載的圖片的柔和色調來改變狀態欄和actionbar的色調,代碼如下

package com.lgl.materialdesign;

import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.drawable.ColorDrawable;
import android.os.Bundle;
import android.support.v7.app.AppCompatActivity;
import android.support.v7.graphics.Palette;
import android.view.Window;
import android.widget.ImageView;

public class MainActivity extends AppCompatActivity {

    private ImageView iv_palette;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        setPalette();
    }

    /**
     * Palette獲取顏色
     */
    private void setPalette() {
        Bitmap bitmap = BitmapFactory.decodeResource(getResources(), R.mipmap.ic_launcher);
        //創建Palette對象
        Palette.generateAsync(bitmap, new Palette.PaletteAsyncListener() {
            @Override
            public void onGenerated(Palette palette) {
                //通過Palette來獲取對應的色調
                Palette.Swatch vibrant = palette.getDarkVibrantSwatch();
                //將顏色設置給相應的組件
                getSupportActionBar().setBackgroundDrawable(new ColorDrawable(vibrant.getRgb()));
                Window window = getWindow();
                window.setStatusBarColor(vibrant.getRgb());
            }
        });
    }
}

而且,我們可以使用不同的方法獲取不同的色調顏色

palette.getVibrantSwatch();
palette.getDarkMutedSwatch();
palette.getLightMutedSwatch();
palette.getMutedSwatch();
palette.getDarkVibrantSwatch();
palette.getLightVibrantSwatch();

看效果

這裡寫圖片描述

4.視圖與陰影

Material Design的一個很重要的特點就是擬物扁平化,如果說IOS的扁平化設計太過於超前,讓很多人來不及從擬物轉變成扁平,那麼Material Design則是把IOS往回拉了一點,通過展現生活中的材料效果,恰當的使用陰影和光線,配合完美的動畫效果,模擬出一個動感十足又美麗大膽的視覺效果

-1.陰影效果

以往的Android View通常有兩個屬性——X和Y,而在Android5.X中,Google為其增加了一個新的屬性——Z,對應垂直方向上的高度變化,看圖,我們更加了解

這裡寫圖片描述

在Android 5.X中,View的Z值由兩部分組成,elevation和translationZ(他們都是Android5.X新引入的屬性),elevation是靜態的成員,translationZ可以在代碼中使用來實現動畫效果,他們的關系

Z = elevation + translationZ;

通過下面的代碼,演示了不同視圖高度所顯示的效果,xml代碼




    

    

    



這裡寫圖片描述

在程序中,我們也可以使用代碼改變視圖高度

 view.setTranslationZ(xxx);

通常也會使用屬性動畫來為視圖高度改變的時候增加動畫效果

    if(flag){
            view.animate().translationZ(100);
            flag = false;
        }else {
            view.animate().translationZ(0);
            flag = true;
        }

5.Tinting 和 Clipping

Android5.X在對圖像的操作有了更多的功能,下面來看看Android5.X的兩個對操作圖像的新功能——Tinting(著色) 和 Clipping(裁剪)

-1.Tinting(著色)

Tinting的使用非常的簡單,只要在XML中配置好tint和tintMode就可以了,對於配置組合效果,只需要大家實際操作一下,就能非常清晰的理解處理效果,在下面的代碼中,設置了幾種不同的tint和tintMode效果,XML代碼如下




    

    

    


    



效果如下

這裡寫圖片描述

Tint通過修改圖像的Alpha遮罩來修改圖像的顏色,從而達到重新著色的目的,這一功能在一些圖片處理的APP使用起來還是十分的方便的

-2. Clipping(裁剪)

Clipping可以讓我們改變一個視圖的外形,要使用Clipping,首先需要使用ViewOutlineProvider來修改outline作用給視圖

下面這個例子,將一個正方形的textview通過Clipping裁剪成一個圓形的正方形和一個圓,XML代碼如下




    

    



邏輯代碼很簡單

 /**
     * Clipping裁剪
     */
    private void setClipping() {
        final View v1 = findViewById(R.id.tv_rect);
        View v2 = findViewById(R.id.tv_circle);

        //獲取Outline
        ViewOutlineProvider vlp1 = new ViewOutlineProvider() {
            @Override
            public void getOutline(View view, Outline outline) {
                //修改outline為特定形狀
                outline.setRoundRect(0, 0, view.getWidth(), view.getHeight(), 30);
            }
        };

        //獲取Outline
        ViewOutlineProvider vlp2 = new ViewOutlineProvider() {
            @Override
            public void getOutline(View view, Outline outline) {
                //修改outline為特定形狀
                outline.setOval(0, 0, view.getWidth(), view.getHeight());
            }
        };
        //重新設置形狀
        v1.setOutlineProvider(vlp1);
        v2.setOutlineProvider(vlp2);
    }

我們看下效果

這裡寫圖片描述

6.列表和卡片

-1.RecyclerView

在Android5.X中將使用了很久的ListView做了升級,增加了一個使用方便,效率更高的控件——RecyclerView,RecyclerView是support-v7中的一個新的組件,是一個強大的滑動控件,ViewHolder的封裝實現,用戶只要實現自己的viewholder就可以了,該組件會自動幫你回收服用的每一個item

要使用RecyclerView,首先需要在項目中引用依賴

compile 'com.android.support:recyclerview-v7:21.0.+'

在布局中使用RecyclerView與使用ListView基本類似,同樣需要一個類似List itemd的布局,在Material Design中,通常與CardView配合使用,後面我們再講CardView的使用

使用RecyclerView的重點和使用和ListView一樣,需要使用一個合適的數據適配器來加載數據,RecyclerView中需要重寫的很多方法都似曾相識,不過RecyclerView更加先進的是,它已經封裝好了ViewHolder,只要實現功能就可以,,先看Adapter

package com.lgl.materialdesign;

import android.support.v7.widget.RecyclerView;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.AdapterView;
import android.widget.TextView;

import java.util.List;

/**
 * RecyclerView的適配器
 * Created by LGL on 2016/4/30.
 */
public class RecyclerAdapter extends RecyclerView.Adapter {

    private List mData;

    public RecyclerAdapter(List mData) {
        this.mData = mData;
    }

    public AdapterView.OnItemClickListener itemClickListener;

    public void setOnItemClickListener(AdapterView.OnItemClickListener itemClickListener) {
        this.itemClickListener = itemClickListener;
    }

    public interface OnItemClickListener {
        void onItemClic(View view, int position);
    }

    @Override
    public ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
        //將布局轉化為View並傳遞給RecyclerView封裝好的ViewHolder
        View v = LayoutInflater.from(parent.getContext()).inflate(R.layout.rc_item, parent, false);
        return new ViewHolder(v);
    }

    @Override
    public void onBindViewHolder(ViewHolder holder, int position) {
        //建立起ViewHolder中視圖和數據的關聯
        holder.textView.setText(mData.get(position) + position);
    }

    @Override
    public int getItemCount() {
        return mData.size();
    }

    public class ViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener {

        private TextView textView;

        public ViewHolder(View itemView) {
            super(itemView);
            textView = (TextView) itemView;
            textView.setOnClickListener(this);
        }

        //通過接口回調來實現RecyclerView的點擊事件
        @Override
        public void onClick(View v) {
            if (itemClickListener != null) {
                itemClickListener.onItemClick(null, v, getPosition(), R.id.tv_item);
            }
        }
    }
}

上面就是一個非常簡單卻典型的RecyclerView,通過onCreateViewHolder將List item的布局轉換成View,並傳遞給RecyclerView封裝好的ViewHolder,就可以將數據和視圖關聯起來了,但是有一點要注意的是,Android並沒有給RecyclerView增進點擊事件,所以我們需要自己寫接口回調,代碼如圖

 public AdapterView.OnItemClickListener itemClickListener;

    public void setOnItemClickListener(AdapterView.OnItemClickListener itemClickListener) {
        this.itemClickListener = itemClickListener;
    }

    public interface OnItemClickListener {
        void onItemClic(View view, int position);
    }

    @Override
    public ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
        //將布局轉化為View並傳遞給RecyclerView封裝好的ViewHolder
        View v = LayoutInflater.from(parent.getContext()).inflate(R.layout.rc_item, parent, false);
        return new ViewHolder(v);
    }

類似ListView的List item視圖




當然,僅僅是性能也是不夠的,讓開發者能夠更加方便的使用才是非常重要的,Google在RecyclerView中定義了LayoutManager來幫助開發者更加方便的創建不同但的布局,下面的例子就演示如何創建水平和垂直布局,當然,你也可以通過自定義LayoutManager來創建自己的布局,核心代碼如下:

   mRcList.setLayoutManager(new LinearLayoutManager(this));
   mRcList.setLayoutManager(new GridLayoutManager(this));

完整代碼:

package com.lgl.materialdesign;

import android.animation.Animator;
import android.animation.AnimatorListenerAdapter;
import android.os.Bundle;
import android.support.v7.app.AppCompatActivity;
import android.support.v7.widget.DefaultItemAnimator;
import android.support.v7.widget.GridLayoutManager;
import android.support.v7.widget.LinearLayoutManager;
import android.support.v7.widget.RecyclerView;
import android.view.View;
import android.widget.AdapterView;
import android.widget.Spinner;

import java.util.ArrayList;
import java.util.List;

public class MainActivity extends AppCompatActivity {

    private RecyclerView mRcList;
    private RecyclerAdapter mAdapter;
    private RecyclerView.LayoutManager mLayoutManager;
    private Spinner mSpinner;
    private ListmData = new ArrayList();

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        mRcList = (RecyclerView) findViewById(R.id.mRcList);
        mLayoutManager = new LinearLayoutManager(this);
        mRcList.setLayoutManager(mLayoutManager);
        mRcList.setHasFixedSize(true);
        //設置顯示動畫
        mRcList.setItemAnimator(new DefaultItemAnimator());

        mSpinner = (Spinner) findViewById(R.id.spinner);
        mSpinner.setOnItemSelectedListener(new AdapterView.OnItemSelectedListener() {
            @Override
            public void onItemSelected(AdapterView parent, View view, int position, long id) {
                if(position == 0){
                    //設置為線性布局
                    mRcList.setLayoutManager(new LinearLayoutManager(MainActivity.this));
                }else if(position == 1){
                    //設置為表格布局
                    mRcList.setLayoutManager(new GridLayoutManager(MainActivity.this,3));
                }else if(position == 2 ){

                }
            }

            @Override
            public void onNothingSelected(AdapterView parent) {

            }
        });
        //增加測試數據
        mData.add("Android Test1");
        mData.add("Android Test2");
        mData.add("Android Test3");

        mAdapter = new RecyclerAdapter(mData);
        mRcList.setAdapter(mAdapter);

        mAdapter.setOnItemClickListener(new AdapterView.OnItemClickListener() {
            @Override
            public void onItemClick(final AdapterView parent, View view, int position, long id) {
                //設置點擊動畫
                parent.animate().translationZ(15f).setDuration(300).setListener(new AnimatorListenerAdapter() {
                    @Override
                    public void onAnimationEnd(Animator animation) {
                        super.onAnimationEnd(animation);
                        parent.animate().translationZ(1f).setDuration(500).start();
                    }
                }).start();
            }
        });
    }

    public void addRecycler(View view){
        int position = mData.size();
        if(position>0){
            mAdapter.notifyDataSetChanged();
        }
    }

    public void delRecycler(View view){
        int position = mData.size();
        if(position>0){
            mData.remove(position-1);
            mAdapter.notifyDataSetChanged();
        }
    }
}

運行結果

這裡寫圖片描述

-2.CardView

CardView曾經開始流行在Google+,後來越來越多的APP也引入了Card這樣的布局方式,說到底,CardView也是一個容器布局,只是他提供了一種卡片的形式,Google所幸提供了一個CardView控件,方便大家使用這種布局,開發者可以設置大小和視圖高度,圓角的角度等,在此之前,我們要添加依賴

 compile 'com.android.support:cardview-v7:21.0.0+'

同時要添加命名空間

xmlns:app="http://schemas.android.com/apk/res-auto"

我們舉個例子

 

        
    

運行的效果

這裡寫圖片描述

7.Activity過渡動畫

這裡寫圖片描述

曾經的Android在activity進行跳轉的時候,只是很生硬的切換,即使通過 overridePendingTransition( int inId, int outId)這個方法來給Activity增加一些切換動畫,效果也只是差強人意,而在Android5.X中,Google對動畫效果進行了更深一步的诠釋,為Activity的轉場效果設計了更加豐富的動畫效果

Android5.X提供了三種Transition類型

進入:一個進入的過渡動畫決定Activity中的所有視圖怎麼進入屏幕 退出:一個退出的過渡動畫決定Activity中的所有視圖怎麼退出屏幕 共享元素:一個共享元素過渡動畫決定兩個Activity之間的過渡,怎麼共享他們的視圖

其中,進人和退出效果包括

explode(分解)一一從屏幕中間進或出,移動視圖 slide(滑動)——從屏幕邊緣進或出,移動視圖 fade(淡出) 一一通過改變屏幕上視圖的不透明度達到添加或者移除視圖

共享元素包括

changeBounds——改變目標視圖的布局邊界 changeCliBounds——裁剪目標視圖邊界 changeTransfrom——改變目標視圖的縮放比例和旋轉角度 changeImageTransfrom——改變目標圖片的大小和縮放比例

可以發現,在Android5.X上,動畫效果的種類變得更加豐富了

首先來看看普通的三種Activity過渡動畫, 要使用這些動畫非常簡單,例如從ActivityA轉到ActivityB,只需要在ActivityA中將基本的startActivity(intent)方法改為如下代碼即可

startActivity(intent, ActivityOptions.makeSceneTransitionAnimation(MainActivity.this).toBundle());

而在AchvityB中,只需要設置下如下所示代碼

 getWindow().requestFeature(Window.FEATURE_CONTENT_TRANSITIONS);

或者在樣式文件中設置如下所示代碼

 true

那麼接下來就可以設置進人/退出ActivityB的具體的動畫效果了, 代碼如下所示

getWindow().setEnterTransition(new Explode());
getWindow().setEnterTransition(new Slide());
getWindow().setEnterTransition(new Fade());

而對於共享元素的動畫效果.可以借用開發者網上的一張圖

這裡寫圖片描述

要想在程序中使用共享元素的動畫效果也很簡單,首先需要在他的activity1布局中設置共享元素,增加元素代碼

android:transitionName="XXX"

同時在activity2中,也增加一個相應的共享元素屬性,如果只要一個共享元素,那麼在activity1中可以這樣寫

startActivity(intent, ActivityOptions.makeSceneTransitionAnimation(this,view,"share").toBundle());

使用的參數就是前面普通動畫的基礎上增加了共享的的view和前面取的名字,如果由多個共享元素,那麼我們可以通過

 Pair.create()

來創建多個共享元素

startActivity(intent, ActivityOptions.makeSceneTransitionAnimation(this, Pair.create(view,"share"),Pair.create(fab,"fab")).toBundle());

下面我們通過一個具體的實例來演示一下過渡動畫,我們從BActivity跳轉到CActivity

BActivity的XML


實現邏輯

package com.lgl.materialdesign;

import android.app.ActivityOptions;
import android.content.Intent;
import android.os.Bundle;
import android.support.annotation.Nullable;
import android.support.v7.app.AppCompatActivity;
import android.util.Pair;
import android.view.View;

/**
 * BActivity
 * Created by lgl on 2016/5/1.
 */
public class BActivity extends AppCompatActivity {

    private Intent intent;

    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_b);


    }

    //設置不同的動畫效果
    public void explode(View view) {
        intent = new Intent(this, CActivity.class);
        intent.putExtra("flag", 0);
        startActivity(intent, ActivityOptions.makeSceneTransitionAnimation(this).toBundle());
    }

    //設置不同的動畫效果
    public void slide(View view) {
        intent = new Intent(this, CActivity.class);
        intent.putExtra("flag", 1);
        startActivity(intent, ActivityOptions.makeSceneTransitionAnimation(this).toBundle());
    }

    //設置不同的動畫效果
    public void fade(View view) {
        intent = new Intent(this, CActivity.class);
        intent.putExtra("flag", 2);
        startActivity(intent, ActivityOptions.makeSceneTransitionAnimation(this).toBundle());
    }

    //設置不同的動畫效果
    public void share(View view) {
        View fab = findViewById(R.id.fab_button);
        intent = new Intent(this, CActivity.class);
        intent.putExtra("flag", 3);
        //創建單個共享元素
        startActivity(intent, ActivityOptions.makeSceneTransitionAnimation(this, view, "share").toBundle());
        //創建多個共享單元
        startActivity(intent, ActivityOptions.makeSceneTransitionAnimation(this, Pair.create(view, "share"), Pair.create(fab, "fab")).toBundle());
    }


}

再看CActivity的XML




    

實現邏輯就更簡單了

package com.lgl.materialdesign;

import android.os.Bundle;
import android.support.annotation.Nullable;
import android.support.v7.app.AppCompatActivity;
import android.transition.Explode;
import android.transition.Fade;
import android.transition.Slide;
import android.view.Window;

/**
 * CActivity
 * Created by LGL on 2016/5/2.
 */
public class CActivity extends AppCompatActivity {

    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        getWindow().requestFeature(Window.FEATURE_CONTENT_TRANSITIONS);
        int flag = getIntent().getExtras().getInt("flag");
        switch (flag) {
            case 0:
                getWindow().setEnterTransition(new Explode());
                break;
            case 1:
                getWindow().setEnterTransition(new Slide());
                break;
            case 2:
                getWindow().setEnterTransition(new Fade());
                getWindow().setExitTransition(new Fade());
                break;
        }
        setContentView(R.layout.activity_c);
    }
}

我們運行一下就可以看到自己想要的效果了

這裡寫圖片描述

八.Material Design動畫效果

動畫已經成了UI設計中一個非常重要的一個組成部分,在Android5.X的Material Design中,更是使用了大量的動畫效果,同時Google官方文檔也有詳細的說明

1.Ripple效果

在Android5.X中,Material Design大量的使用了Ripple動畫,即點就博文效果,可以通過如下代碼設置波紋的背景

//波紋有邊界
 android:background="?android:attr/selectableItemBackground"
 //波紋無邊界
 android:background="?android:attr/selectableItemBackgroundBorderless"

波紋有邊界是指波紋被限制在控件的邊界中,而波紋超出邊界,則是不會受到控件的限制,以圓形發散出去,我們做一個演示

XML


運行的效果

這裡寫圖片描述

同樣的,我們可以寫一個xml文件來實現Ripple效果



    
        
            
        
    

使用方法直接設置背景就可以了,運行效果

這裡寫圖片描述

2.Circular Reveal

這個動畫效果是在Google I/O 大會上演示了好多次的,具體變現為一個View以圓形的形式展開,揭示出來,通過ViewAnimationUtils.createCircularReveal()來創建動畫,代碼如下:

public static Animator createCircularReveal(View view, int centerX, int centerY, float startRadius, float endRadius) {

        return new RevealAnimator(view,centerX,centerY,startRadius,endRadius);
    }

RevealAnimator的使用特別簡單,主要就是幾個關鍵的坐標點

centerX 動畫開始的中心點X centerY 動畫開始的中心點Y startRadius 動畫開始半徑 endRadius 動畫結束半徑

我們還是通過一個實例去演示一下

XML




    

    

邏輯代碼

package com.lgl.materialdesign;

import android.animation.Animator;
import android.os.Bundle;
import android.support.annotation.Nullable;
import android.support.v7.app.AppCompatActivity;
import android.view.View;
import android.view.ViewAnimationUtils;
import android.view.animation.AccelerateDecelerateInterpolator;
import android.view.animation.AccelerateInterpolator;

/**
 * Circular Reveal
 * Created by LGL on 2016/5/2.
 */
public class CirActivity extends AppCompatActivity {

    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_cir);

        final View oval = findViewById(R.id.oval);
        oval.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                Animator animator = ViewAnimationUtils.createCircularReveal(oval, oval.getWidth() / 2, oval.getHeight() / 2, oval.getWidth(), 0);
                animator.setInterpolator(new AccelerateDecelerateInterpolator());
                animator.setDuration(2000);
                animator.start();
            }
        });


        final View rect = findViewById(R.id.rect);
        rect.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                Animator animator = ViewAnimationUtils.createCircularReveal(rect, 0, 0, 0, (float) Math.hypot(rect.getWidth(), rect.getHeight()));
                animator.setInterpolator(new AccelerateInterpolator());
                animator.setDuration(2000);
                animator.start();
            }
        });
    }
}

這樣我們就可以去實現了

這裡寫圖片描述

3. View state changes Animation

在Android5.X中,系統提供了視圖與狀態改變來設置一個視圖狀態的切換

 


StaetListAnimator

 

StaetListAnimator作為視圖改變時的動畫效果,通常會使用Seletor來進行設置,但是以前我們設置Seletor的時候,通常是修改他的背景來達到反饋的效果,但是再現在Android5.X中就不需要這樣了,可以使用動畫來實現,我們用小例子來具體看看怎麼實現的吧
在XML中定義一個StaetListAnimator



    
        
            
    

    
        
            
    

然後直接在布局中設置即可

 

 


animated-selector

 

animated-selector同樣是一個改變動畫效果的動畫,
這個效果不講,沒素材

九.Toolbar

Toolbar和actionBar最大的區別就是Toolbar更加的自由,可控,這也是Google在逐漸使用Toolbar來取代actionBar的原因,要使用Toolbar就必須引用依賴

compile 'com.android.support:appcompat-v7:23.3.0'

同樣的,我們要設置主題

Theme.AppCompat.Light.NoActionBar

然後在XML中

在代碼中獲取

         mToolbar = (Toolbar) findViewById(R.id.toolbar);
        mToolbar.setLogo(R.mipmap.ic_launcher);
        mToolbar.setTitle("主標題");
        mToolbar.setSubtitle("副標題");
        setSupportActionBar(mToolbar);

而menu都是一樣的,就不寫了,這樣一個title就寫出來了

這裡寫圖片描述

我們再來具體實現以下,我們加入一個側滑的效果,XML代碼




    

    

        
        

然後我們設置一下

 mToolbar = (Toolbar) findViewById(R.id.toolbar);
        mToolbar.setLogo(R.mipmap.ic_launcher);
        mToolbar.setTitle("主標題");
        mToolbar.setSubtitle("副標題");
        setSupportActionBar(mToolbar);

        getSupportActionBar().setDisplayHomeAsUpEnabled(true);
        mDrawerLayout = (DrawerLayout) findViewById(R.id.drawer);
        mDrawerToggle = new ActionBarDrawerToggle(this,mDrawerLayout,mToolbar,0,0);
        mDrawerToggle.syncState();
        mDrawerLayout.setDrawerListener(mDrawerToggle);

運行的效果

這裡寫圖片描述

十.Notification

Notification作為一個時間觸發性的交互提示接口,讓我們獲得消息的時候,在狀態欄,鎖屏界面顯示相應的消息

Google在Android5.X中,又進一步的改進了通知欄,優化了Notification,在5.X設備上一個標准的通知是這樣的,長按是下圖

這裡寫圖片描述

長按會顯示消息的來源

Notification會有一個從白色到灰色的動畫切換效果,最終顯示發出這個通知的調用者,而在我們的鎖屏界面,也可以看到

這裡寫圖片描述

我們分四重境界來講解在Android5.X下使用Notification

1.基本的Notification

通過Notification.Builder創建一個Notification的builder,代碼如下

 Notification.Builder builder = new Notification.Builder(this);

這個與AlertDialog的使用方法非常的相似,接下來,要點擊Notification執行一個intent,由於這個intent的不是立即執行,而是用戶觸發的,所以用pendingintent來完成這個延時操作,代碼如下:

Intent intent = new Intent(Intent.ACTION_VIEW, Uri.parse("http://www.baidu.com"));
//構造pendingdintent
PendingIntent pendingIntent = PendingIntent.getActivities(this,0,intent,0);

這樣點擊PendingIntent 之後就會觸發時間了,我們也可以給他增加屬性

        builder.setSmallIcon(R.mipmap.ic_launcher);
        builder.setContentIntent(pendingIntent);
        builder.setAutoCancel(true);
        builder.setLargeIcon(BitmapFactory.decodeResource(getResources(),R.mipmap.ic_launcher));
        builder.setContentText("Title");
        builder.setContentText("內容");
        builder.setSubText("text");

通過下面的代碼發布通知欄

 //通過NotificationManager來發出
        NotificationManager notificationManager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
        notificationManager.notify(0,builder.build());

這樣我們很輕松的就創建了一個通知欄

這裡寫圖片描述

2.折疊式Notification

折疊式Notification也是一種自定義視圖的Notification,常常用於顯示文本,他擁有兩個視圖狀態,我們可以用RemoteView來幫助我們創建一個Notification視圖,代碼如下:

        //通過RemoteViews創建自定義視圖
        RemoteViews contentView = new RemoteViews(getPackageName(),R.layout.notification);
        contentView.setTextViewText(R.id.textView,"通知欄");

其中notification的布局是這樣的




    

    

通過如下代碼,可以講一個視圖指定為Notification正常狀態下的視圖

  notification.contentView = contentView;

另一個展開的代碼

notification.bigContentView = expandedView;

奉獻完整代碼

package com.lgl.materialdesign;

import android.app.Notification;
import android.app.NotificationManager;
import android.app.PendingIntent;
import android.content.Intent;
import android.graphics.BitmapFactory;
import android.net.Uri;
import android.os.Bundle;
import android.support.annotation.Nullable;
import android.support.v7.app.AppCompatActivity;
import android.widget.RemoteViews;

/**
 * Notification
 * Created by LGL on 2016/5/2.
 */
public class NotificationActivity extends AppCompatActivity {

    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_notification);

        Notification.Builder builder = new Notification.Builder(this);

        Intent intents = new Intent(Intent.ACTION_VIEW, Uri.parse("http://www.baidu.com"));
        //構造pendingdintent
        PendingIntent pendingIntent = PendingIntent.getActivities(this, 0, new Intent[]{intents}, 0);

        builder.setSmallIcon(R.mipmap.ic_launcher);
        builder.setContentIntent(pendingIntent);
        builder.setAutoCancel(true);
        builder.setLargeIcon(BitmapFactory.decodeResource(getResources(), R.mipmap.ic_launcher));

        //通過RemoteViews創建自定義視圖
        RemoteViews contentView = new RemoteViews(getPackageName(), R.layout.notification);
        contentView.setTextViewText(R.id.textView, "通知欄");


        Notification notification = builder.build();
        //指定視圖
        notification.contentView = contentView;

        RemoteViews expandedView = new RemoteViews(getPackageName(), R.layout.notification_expanded);

        notification.bigContentView = expandedView;


        //通過NotificationManager來發出
        NotificationManager notificationManager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
        notificationManager.notify(0, builder.build());


    }
}

3.懸掛式Notification

懸掛式Notification是Android5.X新增加的方式,Google希望通過這個方式來給用戶帶來更好的體驗,這種被稱為Headsup的Notification方式,可以在屏幕的上方產生Notification而不打擾用戶的操作

在Android Sample中,Google給我們展示了這個項目,代碼如下:

Notification.Builder builder = new Notification.Builder(this).setSmallIcon(R.mipmap.ic_launcher).setPriority(Notification.PRIORITY_DEFAULT).setCategory(Notification.CATEGORY_MESSAGE).setContentTitle("Headsup Notification").setContentText("I am Headsup Notification");
        Intent push = new Intent();
        push.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
        push.setClass(this,MainActivity.class);
        PendingIntent pendingIntent = PendingIntent.getActivities(this,0, new Intent[]{push},PendingIntent.FLAG_CANCEL_CURRENT);
        builder.setContentText("Android 5.X Headsup Notification").setFullScreenIntent(pendingIntent,true);
        NotificationManager nm = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
        nm.notify(0,builder.build());

效果

這裡寫圖片描述

4.顯示等級的Notification

最後一重境界也就是新加入的一種模式,顯示登記,具體分三級

VISIBILITY_PRIVATE -沒有鎖屏的時候顯示 VISIBILITY_PUBLIC - 表明在任何情況下都會顯示 VISIBILITY_SECRET - 表明在pin,password等安全鎖和沒有鎖屏的情況下顯示

這一章自我感覺沒啥寫的,就一頁,跳過吧,很少的知識點

群英傳到這裡,也就沒有知識點可以將了,最後十三章,是兩個小項目,本來不准備講的,不過看到這個拼圖還是可以講一講的,就准備寫了,2048我很早之前就寫過,這裡就不重復了

 

  1. 上一頁:
  2. 下一頁:
熱門文章
閱讀排行版
Copyright © Android教程網 All Rights Reserved