首頁 收藏 QQ群
 網(wǎng)站導(dǎo)航

ZNDS智能電視網(wǎng) 推薦當(dāng)貝市場

TV應(yīng)用下載 / 資源分享區(qū)

軟件下載 | 游戲 | 討論 | 電視計算器

綜合交流 / 評測 / 活動區(qū)

交流區(qū) | 測硬件 | 網(wǎng)站活動 | Z幣中心

新手入門 / 進(jìn)階 / 社區(qū)互助

新手 | 你問我答 | 免費刷機(jī)救磚 | ROM固件

查看: 13094|回復(fù): 0
上一主題 下一主題
[教程]

《Android Dev Guide》系列教程12:用戶界面之建立對話框Dialogs

[復(fù)制鏈接]
跳轉(zhuǎn)到指定樓層
樓主
發(fā)表于 2013-8-28 16:30 | 只看該作者 回帖獎勵 |倒序瀏覽 |閱讀模式
>
Dialog是一個常見的顯示在當(dāng)前activity之上的小窗口。下面的activity會失去焦點,而dialog回接受用戶輸入。dialog常用在與程序直接相關(guān)聯(lián)的通知和短小的activity中。
Android API支持以下幾種dialog:
它可以包含0、1、2、3個按鈕,或者一個列表或者多選單選按鈕等,它是一個功能最強(qiáng)大的dialog接口,詳細(xì)信息可參考下面的章節(jié)。
它會顯示一個進(jìn)度條或者進(jìn)度環(huán),因為他是AlertDialog的子類,所有野支持按鈕。
用來選擇日期的對話框。
用來選擇時間的。
如果你想要定制自己的dialog,你可以繼承Dialog對象,或者它的任何一個子類,并且定義一個新的布局。
Dialog 總是被當(dāng)做activity的一部分來創(chuàng)建和顯示。你可以在activity的onCreateDialog(int)方法中創(chuàng)建一個dialog。當(dāng)你使用這個方法,android系統(tǒng)會自動的管理每個dialog的狀態(tài)并且關(guān)聯(lián)到所在的activity中,讓這個activity成為dialog的管理者。每個dialog都會繼承activity的某些特性。例如,當(dāng)dialog打開時,按下menu彈出的是所在activity的菜單,調(diào)節(jié)的是所在activity的音量。
注意:如果你決定在onCreateDialog()方法之外建立dialog,他將不會連接到activity中,此時,你可以使用setOwnerActivity(Activity)方法來綁定activity。
當(dāng)你顯示dialog時,調(diào)用showDialog(int)來傳遞一個dialog的id句柄。
當(dāng)一個dialog首次顯示時,android會在實例化dialog的activity中調(diào)用onCreateDialog(int)方法?;卣{(diào)方法會傳遞相同的id給showDialog(int)。當(dāng) 創(chuàng)建完一個dialog后,會再方法的最后返回這個對象。
在dialog顯示前,android回調(diào)用可選的方法 :onPrepareDialog(int,Dialog)。如果你想在每次調(diào)用dialog時改變一些配置的話,你可以定義這個方法。OnPrepareDialog(int,Dialog)方法會在每次調(diào)用dialog時調(diào)用,而onCreateDialog(int)方法只會調(diào)用一次。如果你不定義onPrepareDialog()方法,那么打開的dialog會保持上一次的狀態(tài)。這個方法也會傳遞dialog的id句柄。
定義這兩個onXXX()方法最好使用一個switch結(jié)構(gòu)來檢測Id參數(shù),每一個case項都應(yīng)該創(chuàng)建自己的dialog。例如。想象一個游戲使用兩個不同的dialog,一個暫停一個結(jié)束游戲:
   
   
  1. static final int DIALOG_PAUSED_ID = 0;     
    static final int DIALOG_GAMEOVER_ID = 1;  
復(fù)制代碼
然后,再onCreateDialog(int)里根據(jù)id創(chuàng)建dialog:
   
  1. protected Dialog onCreateDialog(int id) {     
        Dialog dialog;     
        switch(id) {     
        case DIALOG_PAUSED_ID:     
            // do the work to define the pause Dialog     
            break;     
        case DIALOG_GAMEOVER_ID:     
            // do the work to define the game over Dialog     
            break;     
        default:     
            dialog = null;     
        }     
        return dialog;     
    }  
復(fù)制代碼
注意:在例子中沒有詳寫,因為定義dialog屬于另外的章節(jié)?,F(xiàn)在可以調(diào)用showDilaog(int)來顯示一個dialog了:
   
  1. showDialog(DIALOG_PAUSED_ID);  
復(fù)制代碼
調(diào)用dialog的dismiss()方法可以隱藏正在顯示的dialog,如果必要的話,可以調(diào)用activity的dismissDialog(int)方法,他倆效果是一樣的。如果使用的onCreateDialog(int)方法來管理dialog的狀態(tài),那么每次當(dāng)你的dialog消失時,對話框的狀態(tài)都會被activity保存著。如果不太需要這個對話框或者不希望activity保留dialog的狀態(tài),可以調(diào)用removeDialog(int)方法。它會刪除任何關(guān)于dialog的引用,如果dialog正在顯示,此方法會讓dialog隱藏。隱藏dialog監(jiān)聽器的使用如果你想讓activity在dialog隱藏時執(zhí)行某些動作,那么你可以建立一個監(jiān)聽器。首先定義DialogInterface.OnDismissListerner 接口,這個接口只有一個方法,onDismiss(DialogInterface),當(dāng)dialog隱藏時被調(diào)用,然后傳遞OnDismissListener 對象給setOnDismissLister()方法。然而,注意dialog也可以是取消,用戶讓這個dialog取消也是一種特殊的情況。當(dāng)用戶按下back鍵時,或者調(diào)用cancel()方法時會發(fā)生這種情況。當(dāng)一個dialog被取消時,OnDismissLister監(jiān)聽器仍然會收到通知,但如果你喜歡的到明確的取消消息,可以注冊DialogInterface.OnCancelLister監(jiān)聽器。   
AlertDialog時Dialog的子類,Dilaog絕大多數(shù)是這個強(qiáng)大類型,你可以在以下情況下使用:@ 一個標(biāo)題@ 一個文本信息@ 一個兩個或者三個按鈕@ 一個單選或者多選列表建立AlertDialog,使用AlertDialog.Builder子類。使用AlertDialog.Builder(Context)方法來獲得一個Builder,并且使用它的公共方法來定義AlertDialog所有的屬性。最后,調(diào)用create()方法來顯示。下面顯示了如何定義AlertDialog.Builder類的一些屬性,如果在onCreateDialog()方法中使用了例子中的代碼,你可以返回結(jié)果對話框來顯示這個dialog。   
     
創(chuàng)建一個上圖所示包含按鈕的AlertDialog,可以使用setXXXButton()方法:   
  1. AlertDialog.Builder builder = new AlertDialog.Builder(this);     
    builder.setMessage("Are you sure you want to exit?")     
           .setCancelable(false)     
           .setPositiveButton("Yes", new DialogInterface.OnClickListener() {     
               public void onClick(DialogInterface dialog, int id) {     
                    MyActivity.this.finish();     
               }     
           })     
           .setNegativeButton("No", new DialogInterface.OnClickListener() {     
               public void onClick(DialogInterface dialog, int id) {     
                    dialog.cancel();     
               }     
           });     
    AlertDialog alert = builder.create();  
復(fù)制代碼
首先,通過setMessage(CharSequence)為dialog添加一個message,然后通過setCancelable(boolean)方法讓此dialog無法通過按back鍵來取消。每個按鈕都需要調(diào)用setXXXButton()方法,例如setPositiveButton()方法,DialogInterface.OnClickListener()類會定義按下按鈕所要做的處理。注意:每種類型的按鈕只能加一個,這就是說,你不能添加多于一個的positive按鈕。最多能添加三個按鈕,positive, neutral, 和 negative.他們名字所顯示的功能并未實現(xiàn),但能幫你記住要實現(xiàn)的功能。
     
   
如上圖所示,使用setItems()方法添加可選列表:
   
  1. final CharSequence[] items = {"Red", "Green", "Blue"};     
    AlertDialog.Builder builder = new AlertDialog.Builder(this);     
    builder.setTitle("Pick a color");     
    builder.setItems(items, new DialogInterface.OnClickListener() {     
        public void onClick(DialogInterface dialog, int item) {     
            Toast.makeText(getApplicationContext(), items[item], Toast.LENGTH_SHORT).show();     
        }     
    });     
    AlertDialog alert = builder.create();  
復(fù)制代碼
首先,使用setTitle(CharSequence)方法設(shè)置標(biāo)題,然后使用setItem()方法添加可選列表,這個列表會接收一個item數(shù)組來顯示,DialogInterFace.OnClickListener類會定義他們的點擊事件。
  
通過setMultiChoiceItems()方法或 setSingleChoiceItems()方法來分別建立一個多選按鈕列表或者單選列表,如果再onCreateDialog()方法中建立了其中一種列表,android會為你管理這個list。當(dāng)activity處于活動狀態(tài)時,dialog會記住當(dāng)才選中項,如果退出了程序,選擇結(jié)果便會丟失。注意:當(dāng)用戶離開或者暫停activity時,如果你想保存選擇狀態(tài),你必須在整個activity的生命周期中保存這個設(shè)置。永久的保存所選項,甚至當(dāng)前進(jìn)程完全被關(guān)閉,你需要使用數(shù)據(jù)存儲方式來保存。建立一個如上圖所示的列表dialog,代碼和上面的例子相同,只需要把setItems()方法改為setSingleChoiceItems()方法即可。
   
  1. final CharSequence[] items = {"Red", "Green", "Blue"};     
    AlertDialog.Builder builder = new AlertDialog.Builder(this);     
    builder.setTitle("Pick a color");     
    builder.setSingleChoiceItems(items, -1, new DialogInterface.OnClickListener() {     
        public void onClick(DialogInterface dialog, int item) {     
            Toast.makeText(getApplicationContext(), items[item], Toast.LENGTH_SHORT).show();     
        }     
    });     
    AlertDialog alert = builder.create();  
復(fù)制代碼
setSingleChoiseItems()方法的第二個參數(shù)是checkedItem的id值,從0開始對應(yīng)著位置,如果返回”-1“表明沒有選中任何項。
   
     
ProgressDialog時AlertDialog的子類,它會顯示一個表示進(jìn)度的圓形動畫,來表示一個進(jìn)度或者任務(wù)正在運行,也可以時一個進(jìn)度條,能清晰的表示出進(jìn)度。他也能添加按鈕,比如取消一個下載進(jìn)程。調(diào)用ProgressDialog.show()方法可以顯示進(jìn)程對話框,例如,上圖的對話框可通過如下代碼生成:   
  1. ProgressDialog dialog = ProgressDialog.show(MyActivity.this, "",      
                            "Loading. Please wait...", true);  
復(fù)制代碼
第一個參數(shù)是程序的Context引用,四二個為標(biāo)題,第三個為顯示的信息,最后一個為類型,(當(dāng)創(chuàng)建進(jìn)度條時才會用到,下節(jié)討論)。默認(rèn)的進(jìn)度條為圓形的樣式,如果你想生成一個通過具體數(shù)值來顯示任務(wù)的加載情況的進(jìn)度條,下一節(jié)會討論。進(jìn)度條的顯示顯示一個進(jìn)度條要經(jīng)過以下幾個步驟:1-使用ProgressDialog(Context)方法初始化2-使用setProgressStyle(int)方法設(shè)置類型。3-調(diào)用show()方法顯示,或者在onCreateDialog(int)方法里返回一個ProgressDialog。4-你可以調(diào)用setProgress(int)方法,根據(jù)整體的任務(wù)完成度來設(shè)置一個具體進(jìn)度值,或者使用incrementPressBy(int)來設(shè)置一個增長值。例如:
   
  1. ProgressDialog progressDialog;     
    progressDialog = new ProgressDialog(mContext);     
    progressDialog.setProgressStyle(ProgressDialog.STYLE_HORIZONTAL);     
    progressDialog.setMessage("Loading...");     
    progressDialog.setCancelable(false);  
復(fù)制代碼
設(shè)置代碼非常簡單,大部分代碼是在dialog參與進(jìn)程并且更新的功能里。你會發(fā)現(xiàn),另起一個線程來做這個工作是很有必要的,要把消息傳遞給activity的UI線程里需要用到 Handler 消息機(jī)制。如果你并不熟悉使用額外的線程,那么看這個例子:這個例子使用了第二個線程來跟蹤任務(wù)的進(jìn)度(實際上只是在數(shù)值上加到100),線程通過 Handler 發(fā)了一個Message 給主activity,然后主activity更新ProgressDialog。
   
  1. package com.example.progressdialog;     
    import android.app.Activity;     
    import android.app.Dialog;     
    import android.app.ProgressDialog;     
    import android.os.Bundle;     
    import android.os.Handler;     
    import android.os.Message;     
    import android.view.View;     
    import android.view.View.OnClickListener;     
    import android.widget.Button;     
    public class NotificationTest extends Activity {     
        static final int PROGRESS_DIALOG = 0;     
        Button button;     
        ProgressThread progressThread;     
        ProgressDialog progressDialog;     
            
        /** Called when the activity is first created. */     
        public void onCreate(Bundle savedInstanceState) {     
            super.onCreate(savedInstanceState);     
            setContentView(R.layout.main);     
            // Setup the button that starts the progress dialog     
            button = (Button) findViewById(R.id.progressDialog);     
            button.setOnClickListener(new OnClickListener(){     
                public void onClick(View v) {     
                    showDialog(PROGRESS_DIALOG);     
                }     
            });      
        }     
            
        protected Dialog onCreateDialog(int id) {     
            switch(id) {     
            case PROGRESS_DIALOG:     
                progressDialog = new ProgressDialog(NotificationTest.this);     
                progressDialog.setProgressStyle(ProgressDialog.STYLE_HORIZONTAL);     
                progressDialog.setMessage("Loading...");     
                progressThread = new ProgressThread(handler);     
                progressThread.start();     
                return progressDialog;     
            default:     
                return null;     
            }     
        }     
        // Define the Handler that receives messages from the thread and update the progress     
        final Handler handler = new Handler() {     
            public void handleMessage(Message msg) {     
                int total = msg.getData().getInt("total");     
                progressDialog.setProgress(total);     
                if (total >= 100){     
                    dismissDialog(PROGRESS_DIALOG);     
                    progressThread.setState(ProgressThread.STATE_DONE);     
                }     
            }     
        };     
        /** Nested class that performs progress calculations (counting) */     
        private class ProgressThread extends Thread {     
            Handler mHandler;     
            final static int STATE_DONE = 0;     
            final static int STATE_RUNNING = 1;     
            int mState;     
            int total;     
                
            ProgressThread(Handler h) {     
                mHandler = h;     
            }     
                
            public void run() {     
                mState = STATE_RUNNING;        
                total = 0;     
                while (mState == STATE_RUNNING) {     
                    try {     
                        Thread.sleep(100);     
                    } catch (InterruptedException e) {     
                        Log.e("ERROR", "Thread Interrupted");     
                    }     
                    Message msg = mHandler.obtainMessage();     
                    Bundle b = new Bundle();     
                    b.putInt("total", total);     
                    msg.setData(b);     
                    mHandler.sendMessage(msg);     
                    total++;     
                }     
            }     
                
            /* sets the current state for the thread,   
             * used to stop the thread */     
            public void setState(int state) {     
                mState = state;     
            }     
        }     
    }  
復(fù)制代碼
  
如果你想自定義dialog的布局,你可以自己創(chuàng)建一個dialog布局。定義好之后,傳遞根View對象或者資源ID到setContextView(View)方法。例如,如上圖的dialog:1-建立一個xml布局文件custom_dialog.xml;   
   
  1. <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"     
                  android:id="@+id/layout_root"     
                  android:orientation="horizontal"     
                  android:layout_width="fill_parent"     
                  android:layout_height="fill_parent"     
                  android:padding="10dp"     
                  >     
        <ImageView android:id="@+id/image"     
                   android:layout_width="wrap_content"     
                   android:layout_height="fill_parent"     
                   android:layout_marginRight="10dp"     
                   />     
        <TextView android:id="@+id/text"     
                  android:layout_width="wrap_content"     
                  android:layout_height="fill_parent"     
                  android:textColor="#FFF"     
                  />     
    </LinearLayout>  
復(fù)制代碼
  
這個xml在LinearLayout里定義了一個ImageView和TextView。
2-設(shè)置上面的布局為dialog的context view ,并且定義ImageView和TextView兩個元素。
   
   
  1. Context mContext = getApplicationContext();     
    Dialog dialog = new Dialog(mContext);     
    dialog.setContentView(R.layout.custom_dialog);     
    dialog.setTitle("Custom Dialog");     
    TextView text = (TextView) dialog.findViewById(R.id.text);     
    text.setText("Hello, this is a custom dialog!");     
    ImageView image = (ImageView) dialog.findViewById(R.id.image);     
    image.setImageResource(R.drawable.android);  
復(fù)制代碼
實例化dialog后,使用setContextView(int)方法設(shè)置自定義的布局?,F(xiàn)在dialog便有了一個自定義的布局,你可以使用findViewById(int)方法來獲得或者修改布局。3-完成了,現(xiàn)在你可以顯示自定義的dialog了。一個dialog必須有一個title,如果你沒有調(diào)用setTitile()方法,那么會標(biāo)題處會顯示空,但dialog仍然可見,如果你不想顯示標(biāo)題,只有寫一個自己的dialog類了。然而,因為一個AlertDialog使用AlertDialog.builder類創(chuàng)建起來非常簡單,你不必使用setContextView(int)方法。但必須使用setView(view)方法代替。這個方法會接受一個view參數(shù),你需要從xml中得到根view元素。得到xml布局,通過LayoutInflater類的getLayoutflater()方法(或者getSystemService()方法),然后調(diào)用inflate(int,ViewGroup)方法,第一個參數(shù)是xml文件id,第二個參數(shù)是根view的id,在這點上,你可以使用inflated 布局來獲得xml中的view對象并且定義ImageView和TextView對象,然后實例化AlertDialog.Builder類并且使用setView(View)方法來設(shè)置布局。這有一個自定義dialog布局文件的例子:
   
  1. AlertDialog.Builder builder;     
    AlertDialog alertDialog;     
    Context mContext = getApplicationContext();     
    LayoutInflater inflater = (LayoutInflater) mContext.getSystemService(LAYOUT_INFLATER_SERVICE);     
    View layout = inflater.inflate(R.layout.custom_dialog,     
                                   (ViewGroup) findViewById(R.id.layout_root));     
    TextView text = (TextView) layout.findViewById(R.id.text);     
    text.setText("Hello, this is a custom dialog!");     
    ImageView image = (ImageView) layout.findViewById(R.id.image);     
    image.setImageResource(R.drawable.android);     
    builder = new AlertDialog.Builder(mContext);     
    builder.setView(layout);     
    alertDialog = builder.create();  
復(fù)制代碼
使用自定義布局這種方式來生成dialog,可以讓你使用更高級的特性,比如管理按鈕、列表、標(biāo)題、圖標(biāo)等。   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   
   

上一篇:最新的Android開發(fā)工具包可以用來開發(fā)老版本的程序嗎?
下一篇:Android 基本界面-按鈕控件
您需要登錄后才可以回帖 登錄 | 立即注冊

本版積分規(guī)則

Archiver|新帖|標(biāo)簽|軟件|Sitemap|ZNDS智能電視網(wǎng) ( 蘇ICP備2023012627號 )

網(wǎng)絡(luò)信息服務(wù)信用承諾書 | 增值電信業(yè)務(wù)經(jīng)營許可證:蘇B2-20221768 丨 蘇公網(wǎng)安備 32011402011373號

GMT+8, 2024-10-19 14:31 , Processed in 0.076003 second(s), 15 queries , Redis On.

Powered by Discuz!

監(jiān)督舉報:report#znds.com (請將#替換為@)

© 2007-2024 ZNDS.Com

快速回復(fù) 返回頂部 返回列表