Material Design & Android 5

最近研究了一下Material Design和Android 5的新特性,這裏作下總結概括。html

Material Design在我認爲就是相似於卡片同樣的設計,固然並不僅是卡片,material design能夠把一個佈局或者控件當作實際生活中得一個卡片來對待。android

那麼具備如下幾個方面的屬性(具體參照 http://www.google.com/design/spec/material-design/introduction.html 上面某些效果看起來仍是挺炫的):git

  1. 物理屬性——卡片是三維的,在z座標上只有1dp厚;具備投影,不一樣高度的投影效果不同;任何顏色、形狀和內容均可以在material上顯示且不增長厚度;卡片之間不能相互重疊,相互穿過,阻塞點擊觸摸事件。
  2. 變換屬性——能夠改變形狀、合併、拆分而後合併,但不能夠彎曲和摺疊。
  3. 運動屬性——能夠天然的被建立或者銷燬,能夠任意移動,用戶與material的交互通常經過z軸變化和波紋動畫展現

同時material design定義了許多了規範,是通過google產品設計工程師用心總結起來,整體看起來體驗蠻炫。具體效果能夠參照chrome的新書籤,感受比之前高大上許多。在手機設備上也定義了一些規範,這裏只總結我的較爲關注和在手機上比較好實現的一些規範。github

  佈局:layout通常內容距離邊界邊距爲16dpchrome

  可觸摸控件:大小通常爲48*48dp,實際內容爲40*40或者24*24dpapi

   imageView能夠經過設置padding來實現或者讓設計截圖留好padding緩存

  相似按鈕這樣的可觸摸控件通常可觸摸高度爲48dp,實際高度爲36dp網絡

  那麼在安卓內該如何實現這樣的按鈕?app

  It's big problem,這裏想到了兩種方式,但沒有徹底實現:
less

  1. 經過自定義背景來設置,
  2. 調用父類View中得setTouchDelegate方法來擴大button的可觸摸範圍,但一個父類只能設置一個TouchDelegate,當有多個button要實現這樣的可觸摸範圍時,能夠考慮繼承默認的TouchDelegate類,內部本身定義多個可點擊範圍來實現對多個button的委託訪問。
  3. 聽之任之……

material design定義了button控件有三種模式,以下圖:

分別爲:

  1. Floating action button——官方無實現,我在目前開發設計業沒有用到過若是須要使用能夠參照github:https://github.com/futuresimple/android-floating-action-button
  2. Raised button——普通的button,5以上經過使用material相關主題實現波紋和陰影效果;5如下不推薦實現波紋效果,Chris Banes回覆說「Ripples are highly dependent on Lollipop's new RenderThread for performance. As devices before that do not have RT, the performance will be bad.」5如下建議使用Appcompat theme,須要陰影須要本身設置陰影或者使用對應的效果圖。
  3. Flat button——一、設置stateListAnimator,elevation,translationZ爲0;二、api在11以上設置background爲?android:attr/selectableItemBackground(按鈕默認顏色爲透明);

這三種按鈕建議使用頻率是 flat button>raised button>floating action button,主要是爲了不過多的層疊

後面還列出一些其餘material design列出的規範:

Dividers——1dp thick,opacity 12% black or 12% white

Snackbars & toasts 

Single-line snackbar height: 48dp

Multi-line snackbar height: 80dp

Text: Roboto Regular 14sp

Action button: Roboto Medium 14sp, all-caps text

Default background fill: #323232 100%

 

Android 5關於material design實現

以上內容是關於對於material design的一個簡單介紹和我的概括,不少具體規範能夠參照官方material design手冊,設計應該比碼農要關注更多吧,讀完但是要費蠻多功夫的。後面的內容是我的使用Android對material design的實現,其中有一部分摘自於網絡內容,尤爲是圖片,算我盜版唄。

首先,Android 5提供了material theme實現了大多數的控件的樣式,可是我的推薦使用Appcompat包得Theme.AppCompat,其實際上就是繼承了material theme,並實現了對5下部分控件的兼容,material design有如下主題能夠選擇:

Theme.Material (dark version)

Theme.Material.Light (light version)

Theme.Material.Light.DarkActionBar

Theme.AppCompat

Theme.AppCompat.Light

Theme.AppCompat.Light.NoActionBar

Theme.AppCompat.NoActionBar

其次,要配置調色板,通常能夠配置的顏色如圖所示:

其代碼大概能夠是

<resources>
  <style name="AppTheme" parent="android:Theme.Material">
    <item name="android:colorPrimary">@color/primary</item>
    <item name="android:colorPrimaryDark">@color/primary_dark</item>
    <item name="android:colorAccent">@color/accent</item>
  </style>
</resources>

這部分具體在個人demo中以下:

<style name="AppBaseTheme" parent="Theme.AppCompat.Light.NoActionBar">
        <!-- 主要文字顏色 -->
        <item name="android:textColorPrimary">#ffaa66cc</item>

        <!-- 窗口的背景顏色 -->
        <!--<item name="android:windowBackground">@android:color/white</item>-->

        <!-- 默認switch顏色 -->
        <item name="colorSwitchThumbNormal">#ffcc0000</item>
        <item name="colorControlActivated">#ff669900</item>
        <item name="toolbarStyle">@style/MyToolBar</item>
        <item name="switchStyle">@style/MySwitch</item>
        <item name="searchViewStyle">@style/MySearchViewStyle</item>
    </style>

    <style name="AppTheme" parent="@style/AppBaseTheme"/>
MyAppTheme
 <application
        android:name=".common.MyApplication"
        android:allowBackup="true"
        android:icon="@mipmap/ic_launcher"
        android:label="@string/app_name"
        android:theme="@style/AppTheme">
        ...    
AndroidManifest.xml--begin

其中涉及到material design提到的三種組件:

System bar(Status bar) ——即android手機顯示電量,時間等狀態的系統轉太爛;height:24p ,color:通常暗色,也能夠設計爲應用的一種元素色或者半透明

Android navigation bar —— android的導航欄,這裏指左右導航欄,其實安卓手機底部的有返回鍵、home鍵的這一欄也稱爲navigation bar,在屏幕上的時虛擬導航欄,是在手機硬件上得稱爲硬件導航欄;height:48p,color:同status bar側邊導航;推薦:左導航右是當前頁的二級內容 width=Screen width - 56dp;最大width:左320dp,右:全屏

Tools bar -> App bar (Action bar),即系統狀態欄下應用的標題欄,過去是action bar,如今通常用toolbar;橫屏48dp 豎屏最小56dp,菜單欄通常是一個薄紙片,而不是bar的一個擴展

 這裏關於系統的狀態欄和底部導航欄有些配置,介紹以下:

隱藏StatusBar——一、style定義android:windowFullScreen爲true;二、getWindow().addFlags(WindowManager.LayoutParams.FLAY_FULLSCREEN);三、View.setSystemUiVisibility(View.SYSTEM_UI_FLAG_FULLSCREENSYSTEM_UI_FLAG)

隱藏NavigationBar(API 14)——view.setSystemUiVisibility(View.SYSTEM_UI_FLAG_HIDE_NAVIGATION|View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY);

設置顏色(API 21)——getWindow().setStatusBarColor(…);getWindow().setNavigationBarColor();

設置透明(API 14)

getWindow().addFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS);

getWindow().addFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_NAVIGATION)

能夠經過View的一些常量來改變屏幕的一些特性(View.setSystemUiVisibility(UiOptions)(API 11)),具體以下(隱藏系統欄和低能模式會在有app bar時失效):

SYSTEM_UI_FLAG_FULLSCREEN   全屏隱藏系統狀態欄 (lean back)模式

SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN   全屏可是不隱藏系統狀態欄

SYSTEM_UI_FLAG_HIDE_NAVIGATION 全屏並隱藏導航欄

SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION 全屏不隱藏導航欄

SYSTEM_UI_FLAG_LOW_PROFILE 低能狀態

SYSTEM_UI_FLAG_LAYOUT_STABLE 保持狀態欄和導航欄佈局穩定,相似於invisible

SYSTEM_UI_FLAG_IMMERSIVE immersive 模式

SYSTEM_UI_FLAG_IMMERSIVE_STICKY  不清除flag的immersive模式,過一段時間隱藏的系統欄和導航欄會再次自動隱藏

 具體效果參照demo的StatusBarActivity。

Ripple效果(波紋效果)

  1. 其餘控件能夠設置背景爲?android:attr/selectableItemBackground(API 11)或者?android:attr/selectableItemBackgroundBorderless(API 21),點擊觸摸顏色能夠經過android:colorControlHighlight(API 21)來設置
  2. 使用ViewAnimationUtils.createCircularReveal來實現
  3. 新建一個RippleDrawable資源,賦值給backgroud。
<ripple xmlns:android="http://schemas.android.com/apk/res/android"
        android:color="@android:color/holo_red_dark"><item
        android:drawable="@android:color/holo_green_dark"/></ripple>`
ripple drawable

兼容的使用Android 5.0新特性

  • 使用AppCompat-v7包和Theme.Appcompat主題,提供瞭如下控件的兼容性,(極力推薦,對於不滿意的地方只要去修改style就行了):

Everything provided by AppCompat’s toolbar (action modes, etc)

EditText

Spinner

CheckBox

RadioButton

SwitchCompat

CheckedTextView

  • 定義不一樣的styles,這種方式還好,能夠同時繼承一個低版本的父類style,而後不一樣機型實現不一樣效果

     res/values/styles.xml.

  

<style name="AppBaseTheme" parent="Theme.AppCompat.Light">
        <item name="windowActionBar">false</item>
        <item name="windowNoTitle">true</item>
        <!-- 主要文字顏色 -->
        <item name="android:textColorPrimary">#ffaa66cc</item>
        <item name="android:textColorHighlight">@color/abc_primary_text_material_dark</item>

        <item name="colorPrimaryDark">#ffaa66cc</item>
        <item name="colorPrimary">#ffaa66cc</item>
        <item name="colorAccent">?attr/colorAccent</item>
        <!-- 窗口的背景顏色 -->
        <!--<item name="android:windowBackground">@android:color/white</item>-->

        <!-- 默認switch顏色 -->
        <item name="colorSwitchThumbNormal">#ffcc0000</item>
        <item name="colorControlActivated">#ff669900</item>
        <item name="toolbarStyle">@style/MyToolBar</item>
        <item name="switchStyle">@style/MySwitch</item>
        <item name="searchViewStyle">@style/MySearchViewStyle</item>
        <item name="editTextStyle">@style/Widget.AppCompat.EditText</item>
        <item name="buttonStyle">@style/MyButton</item>
        <item name="dialogTheme">@style/Theme.AppCompat.Light.Dialog</item>
    </style>
style

     res/values-v21/styles.xml.

<resources xmlns:android="http://schemas.android.com/apk/res/android">

    <style name="AppTheme" parent="@style/AppBaseTheme">
        <!-- 系統狀態欄 顏色-->
        <item name="android:colorPrimaryDark">@android:color/holo_green_dark</item>
        <!-- 底部導航欄顏色 -->
        <item name="android:navigationBarColor">@android:color/holo_purple</item>

        <item name="android:colorAccent">?attr/colorAccent</item>
        <!-- 觸摸顏色,包括button ripple 背景-->
        <item name="android:colorControlHighlight">@android:color/holo_red_dark</item>
    </style>


</resources>
style-v21

 

  • 定義不一樣的佈局,若是真的是佈局會有不一樣,感受大事不妙,在如今的技術基礎上,只要是兩份相同的佈局文件便會遇到維護性難的問題,因此最好仍是保持一致性,若是某些新特性須要修改的話仍是建議使用代碼來實現,能夠採起工廠模式實現不一樣版本特性的抽離:

     res/layout/my_activity.xml 

     res/layout-v21/my_activity.xml

  

Android 5新控件

RecyclerView

RecyclerView是官方首先推出來的一個大控件,官方但願關於展現集合類型的數據均用Recyclerview來實現,能夠用來替代listview和gridview;他對比listview和gridview有如下特色

  • 抽象出了viewholder來緩存view,recyclerview直接管理的時viewholder,再也不是view
  • 對比listview,gridview,它更高效,擁有更大的靈活性,方便的使用不一樣類型的數據,提供輔助類配置動畫
  • 可是須要寫更多的代碼,沒有默認的adapter提供,除了scroll監聽不提供其餘監聽
  • 經過Adapter的細粒度的封裝使得效率提升,譬如增、刪、改某個元素或者某個範圍的元素經過調用notifyItemChanged(int position)、notifyItemInserted(int position)、notifyItemMoved(int fromPosition, int toPosition)、notifyItemRangeChanged(int positionStart, int itemCount)等方法實現,再也不像listview必須一次性通知更改所有集合元素。

 簡單使用:

StaggeredGridLayoutManager指佈局按照瀑布流模式來排列布局
 1 private void initRecycler() {
 2         // use this setting to improve performance if you know that changes
 3 
 4         RecyclerView.LayoutManager layoutManager = new StaggeredGridLayoutManager(3, OrientationHelper.VERTICAL);
 5         RecyclerView.LayoutManager layoutManager1 = new LinearLayoutManager(this, LinearLayoutManager.VERTICAL, false);
 6         RecyclerView.LayoutManager layoutManager2 = new LinearLayoutManager(this, LinearLayoutManager.HORIZONTAL, false);
 7         RecyclerView.LayoutManager layoutManager3 = new GridLayoutManager(this, 3);
 8         mRecyclerView.setLayoutManager(layoutManager);
 9         mRecyclerView.setAdapter(new Adapter(Arrays.asList("button & background", "status bar & nav bar",
10                 "cardView & ripple", "toolbar", "switchCompat", "exit", "add1", "add2")));
11         // in content do not change the layout size of the RecyclerView
12         mRecyclerView.setHasFixedSize(false);
13     }
recyclerView init
  1 private class Adapter extends RecyclerView.Adapter<RecyclerView.ViewHolder> implements View.OnClickListener {
  2         private List<String> list;
  3         private OnItemClickListener listener;
  4 
  5         public Adapter(List<String> list) {
  6             super();
  7             this.list = new ArrayList<>(list);
  8             listener = new OnItemClickListener() {
  9                 @Override
 10                 public void onItemClick(View v, int layoutPosition) {
 11                     onClick(v);
 12                 }
 13             };
 14         }
 15 
 16         @Override
 17         public RecyclerView.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
 18             Context context = parent.getContext();
 19             if (viewType == 1) {
 20                 ImageView imageView = new ImageView(context);
 21                 imageView.setLayoutParams(new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, 150));
 22                 return new MyViewHolder(new ImageView(context));
 23             }
 24             Button btn = new Button(context);
 25             btn.setMinHeight((int) (context.getResources().getDisplayMetrics().density * (36 + random.nextInt(36) + 0.5f)));
 26             return new MyViewHolder(btn);
 27         }
 28 
 29         @Override
 30         public void onBindViewHolder(RecyclerView.ViewHolder holder, int position) {
 31             if (position != getItemCount() - 1) {
 32                 ((Button) holder.itemView).setText(list.get(position));
 33             } else {
 34                 ((ImageView) holder.itemView).setImageResource(R.mipmap.ic_launcher);
 35             }
 36         }
 37 
 38         @Override
 39         public int getItemViewType(int position) {
 40             if (position == getItemCount() - 1) {
 41                 return 1;
 42             }
 43             return super.getItemViewType(position);
 44         }
 45 
 46         @Override
 47         public int getItemCount() {
 48             return list == null ? 0 : list.size() + 1;
 49         }
 50 
 51         public void add(int position, String str) {
 52             list.add(position, str);
 53             notifyItemInserted(position);
 54         }
 55 
 56         public void delete(int position) {
 57             list.remove(position);
 58             notifyItemRemoved(position);
 59         }
 60 
 61         @Override
 62         public void onClick(View v) {
 63             int index;
 64             switch ((String) v.getTag()) {
 65             case "button & background":
 66                 if (Utils.hasLollipop()) {
 67                     getWindow().setExitTransition(new Fade());
 68                 }
 69 
 70                 startActivity(
 71                         new Intent(HomeActivity.this, ButtonActivity.class),
 72                         ActivityOptions.makeCustomAnimation(HomeActivity.this, android.R.anim.fade_in,
 73                                 android.R.anim.slide_out_right).toBundle());
 74                 break;
 75             case "status bar & nav bar":
 76                 startActivity(new Intent(HomeActivity.this, StatusBarActivity.class));
 77                 break;
 78             case "cardView & ripple":
 79                 startActivity(new Intent(HomeActivity.this, CardViewActivity.class));
 80                 break;
 81             case "toolbar":
 82                 startActivity(new Intent(HomeActivity.this, ToolBarActivity.class));
 83                 break;
 84             case "switchCompat":
 85                 startActivity(new Intent(HomeActivity.this, SwitchActivity.class));
 86                 break;
 87             case "exit":
 88                 exit();
 89                 break;
 90             case "delete 1":
 91                 delete(list.indexOf("delete 1"));
 92                 break;
 93             case "delete 2":
 94                 delete(list.indexOf("delete 2"));
 95                 break;
 96             case "add1":
 97                 index = list.indexOf("delete 1");
 98                 if (index < 0) {
 99                     add(list.indexOf("add1"), "delete 1");
100                 }
101                 break;
102             case "add2":
103                 index = list.indexOf("delete 2");
104                 if (index < 0) {
105                     add(list.indexOf("add1"), "delete 2");
106                 }
107                 break;
108             }
109         }
110 
111         private class MyViewHolder extends RecyclerView.ViewHolder {
112             public MyViewHolder(View itemView) {
113                 super(itemView);
114 
115                 if (listener != null) {
116                     itemView.setOnClickListener(new View.OnClickListener() {
117                         @Override
118                         public void onClick(View v) {
119                             if (v.getTag() == null) {
120                                 v.setTag(list.get(getLayoutPosition()));
121                             }
122                             listener.onItemClick(v, getLayoutPosition());
123                         }
124                     });
125                 }
126             }
127 
128             @Override
129             public String toString() {
130                 return super.toString();
131             }
132         }
133     }
定義Adapter

其中,onCreateViewHolder方法用來建立對應的Viewholder,onBindViewHolder用來指定當viewholder被綁定時該作什麼操做,getItemViewType方法指定數據類型,好生成不一樣類型的View。

 

PS:

Recyclerview內部定義的position有兩種position,他們在大多時候相同,僅在某些狀況下不一致,以下:

  • layout position: 指的是你所能看到的item的position.
  • adapter position: item在adapter的position,只在調用adapter.notify*時會不一樣(二者大概差16ms),獲取該position的方法可能會返回NO_POSITION或者null.

CardView

官方上說list大多數狀況是瓷磚,四角方方正正,但cardview是真的卡片。那麼CardView在android的實現其實能夠設置圓角自帶陰影的FrameLayout,適用狀況:文字內容在三行以上,一個佈局有兩個以上的動做事件;其餘狀況請酌情考慮使用list,不要濫用。如下是幾個要點:

  • cardView在5如下使用了padding來繪製陰影,因此cardview的padding在5如下無效,建議使用setContentPadding(int, int, int, int) 來設置內容和邊界的padding
  • 若是給cardview指定了準確的大小,那麼cardview在5之前和5之後的版本會有一些差異,能夠經過兼容的resource來解決該差別,也能夠經過setUseCompatPadding(true)來設置5之後的cardview也使用內部padding來解決該差別
  • 經過設置 setCardElevation(float)來改變海拔高度,同時改變陰影大小;只改變陰影大小,不改變z座標使用 setMaxCardElevation(float)

 

Palette

palette是官方給的一個新API,能夠從一個圖片抽取6種不一樣元素的顏色,這個API使得android的界面能夠顯得更加富有變化和活潑,好比在一個listview中,抽取每一個item的圖片來做爲這個item的標題欄,來區分這個item和其餘item的顏色分類;或者抽從app的一個主要圖片抽取顏色賦予到status bar等等。

官方的這個類只提供了6種顏色,其實也是提取某些範圍的顏色值,提取出來的顏色是徹底不透明的。具體用法以下:

 1 build = Palette.from(((BitmapDrawable) getResources().getDrawable(R.mipmap.ic_launcher)).getBitmap())
 2                 .maximumColorCount(16).resizeBitmapSize(192);
 3 build.generate(new Palette.PaletteAsyncListener() {
 4                 @Override
 5                 public void onGenerated(Palette palette) {
 6                     Palette.Swatch swatch = palette.getVibrantSwatch();
 7                     int tc = swatch.getTitleTextColor(), bc = swatch.getBodyTextColor();
 8                     if (Utils.hasLollipop()) {
 9                         getWindow().setStatusBarColor(swatch.getRgb());
10                     }
11                 }
12             });

PS:建議使用22.1以上的support包,效率會提高5倍以上

 

AppCompatActivity & Toolbar

AppCompatActivity用來代替ActionBarActivity,提供在安卓全部版本一致性的App bar,即Toolbar。AppCompatActivity要求使用Theme.AppCompact主題或者該主題的子類。之後建議使用AppCompatActivity來當作全部activity的父類。

那麼如今有個問題,咱們爲何要使用toolbar,我我的總結了如下三點緣由:

  1. google推material design,toolbar做爲一個重點來推,他們認爲這樣的設計是一個好的設計
  2. toolbar提供了以前actionbar幾乎全部的功能(有些被廢棄但依然很強大),有利於保持設計的一致性,而且保持了靈活性和擴展性
  3. toolbar是個相似於RelativeLayout的viewgroup,子view支持layout_gravity屬性,能夠自由擴展;之前須要費勁的擴展actionbar的瓶頸已經不復存在,你想怎麼擴展就怎麼擴展!

那麼ToolBar默認提供了哪些強大的功能:

  1. 和DrawerLayout良好配合實現「抽屜」導航欄
  2. 提供可摺疊的視圖(CollapsibleActionView),官方已提供searchview的實現。
  3. 提供了action provider,能夠展現一個子菜單,官方提供了ShareActionProvider,MediaRouteActionProvider

如下三張圖分別展現了這三個功能,具體示例和實現能夠參照demo

 

 

toolbar默認元素圖以下:

若是但願toolbar充當如圖系統中的app bar,那麼須要在OnCreate中調用setSupportActionBar(toolbar),這時toolbar即成爲系統的app bar,擁有action bar絕大多數功能。

設置NavigationIcon,需在setSupportActionBar後調用toolbar.setNavigationIcon;

設置Logo,主標題和副標題調用setLogo、setTitle、setSubTitle便可。若是不但願顯示toolbar自帶的標題,那麼能夠設置標題爲"",注意爲null無效;或者設置getSupportActionBar().setDisplayShowTitleEnabled(false);

設置toolbar的NavigationIcon隨着drawerlayout的抽屜變化而改變圖標,設置getSupportActionBar().setDisplayHomeAsUpEnabled(true)和getSupportActionBar().setHomeButtonEnabled(true);

設置右側菜單,需在activity的onCreateOptionsMenu方法中設置本身的菜單,而後能夠在onOptionsItemSelected方法中捕獲到每一個菜單被選擇到獲得的事件,也能夠toolbar本身設置監聽;

 

額外的一些分享

退出系統

在android 5要退出應用通常啓動app的一個singleTop的activity,而後再finish這個activity。在android 5以上不推薦由咱們來退出程序,應該交給系統來完成這樣的工做,若是在android 5仍是須要這樣的功能,能夠經過下面簡單的代碼實現:

1 List<ActivityManager.AppTask> list = activityManager.getAppTasks();
2for (ActivityManager.AppTask appTask : list) {
    appTask.finishAndRemoveTask();

3 }
exit

判斷當前activity是否正在運行

在android 5之前都是經過拿getRuningTask來獲取相關信息,可是如今android 5認爲這個方法會泄露隱私,所以廢棄了getRuningTask等方法,所以在android 5以上須要經過runningAppProcessInfo來獲取相關信息,具體代碼以下:

1 boolean isOnForeGround = false;
List<ActivityManager.RunningAppProcessInfo> pList =activityManager.getRunningAppProcesses();
for(ActivityManager.RunningAppProcessInfo processInfo : pList){
    if(processInfo.importance == ActivityManager.RunningAppProcessInfo.IMPORTANCE_FOREGROUND){
        
2 for(String activityPack : processInfo.pkgList){
            if(activityPack.equals(context.getPackageName())){
                isOnForeGround = true;
                
3 return;
            
4 }

5         }
6 
    }
}
activity is foreground ?

更改背景的透明度和灰度(API 1)

即更改如彈出dialog默認的背景,能夠由下面代碼來作

1 WindowManager.LayoutParams lp = dialog.getWindow().getAttributes();

2 lp.alpha = 0.5f;
3 lp.dimAmount = 0.6f;

4 dialog.getWindow().setAttributes(lp);
dialog.getWindow().setFlags(WindowManager.LayoutParams.FLAG_DIM_BEHIND,
        WindowManager.LayoutParams.FLAG_DIM_BEHIND);
dim background

 

大概總結這麼多,demo下載地址

https://github.com/jonyChina162/LollipopTest

裏面還有我本身作的一個ppt

相關文章
相關標籤/搜索