android之旅-Intent和BroadcastReceiver(修改了網上文章很多不足,重點參考了android4進階編程)

來源:互聯網
上載者:User

android之旅-Intent和BroadcastReceiver(修改了網上文章很多不足,重點參考了android4進階編程)

一、Intent作用及分類

Intent是一種訊息傳遞機制,可以在程式內及程式間使用,主要用法為:①使用類名顯式啟動一個service或Activity②在①的基礎上執行一個動作的intent,並進行相關處理③廣播某個時間已經發生。

二、使用Intent啟動Activity

1、顯式啟動一個Activity

所謂顯式啟動,即顯式指定我們要啟動Activity的類名,比如我們要在Mainactivity中的Button被按下時,開啟IntentActivity,就可以使用下面的代碼:

 

if(v==btn1){Intent intent=new Intent();intent.setClass(MainActivity.this, IntentActivity.class);startActivity(intent);}
注意,所有的Activity都儲存於一個Activity棧,當我們調用startActivity後,IntentActivity將會經過Creat start resume最終運行,並且IntentActivity會移動到Acticity棧的頂部。但是當我們按下back(或在代碼執行finish())會從Activity棧棧頂依次刪除Activity。

 

2、隱式啟動Activity

隱式啟動Activity即匿名啟動某一恰當的程式組件來響應動作請求。如我們要隱式的啟動開啟連絡人的Activity:

 

//隱含選取連絡人,注意使用startActivity並不能啟動介面Intent intent=new Intent(Intent.ACTION_PICK,Uri.parse(content://contacts/people));startActivityForResult(intent,PICK_CONTACT_SUBACTIVITY);
3、啟動Activity並捕獲子Activity返回的結果

 

在上文我們可以看出,單純使用startActivity MainActivity並不能得到IntentActivity進行處理後的結果。這時我們需要startActivityForResult:

但是僅僅使用這個介面還不夠,我們需要一個介面來監聽結構,這時,我們就需要重載MainActivity中的protected void onActivityResult(int requestCode, int resultCode, Intent data):

在MainActivity中:

 



//定義intent識別碼 private static final int SHOW_SUBACTIVITY=1;
Intent intent=new Intent(); intent.setClass(MainActivity.this, IntentActivity.class); //傳入識別碼唯一標識SHOW_SUBACTIVITY,啟動intent,以便擷取下一頁面返回的結果 startActivityForResult(intent, SHOW_SUBACTIVITY);

 @Overrideprotected void onActivityResult(int requestCode, int resultCode, Intent data) {// TODO Auto-generated method stub    super.onActivityResult(requestCode, resultCode, data);    if(requestCode==SHOW_SUBACTIVITY)    {    switch (resultCode) {    case RESULT_CANCELED:    {    Bundle bd=data.getExtras();    edittxt.setText(bd.getString(text));    break;    }    case RESULT_OK:    {    Bundle bd=data.getExtras();    edittxt.setText(bd.getString(text));    break;    }    default:    break;    }    }}




 

在IntentActivity中:

 

switch(v.getId()){case R.id.resultcancel:{Intent intent=new Intent();intent.setClass(IntentActivity.this, MainActivity.class);intent.putExtra(text, cancel:i am from intentactivity!and pass back me on childactivity finished!);setResult(RESULT_CANCELED,intent);finish();break;}case R.id.resultok:{Intent intent=new Intent(); intent.setClass(IntentActivity.this, MainActivity.class); intent.putExtra(text, ok: am from intentactivity!and pass back me on childactivity finished!); setResult(RESULT_OK,intent); finish(); break;}default:break;}
解析:我們在startActivityForResult(intent, SHOW_SUBACTIVITY);傳入SHOW_SUBACTIVITY,其實就是一個大於0的整數,用來標識相應的Intent;為了接受Result,對onActivityResult(int requestCode, int resultCode, Intent data) 進行重寫,注意,requestCode就是Intent的標識符,即為上文中的SHOW_SUNACTIVITY,resultCode即為IntentActivity中的setResult(RESULT_OK,intent);傳回的Result值 -RESULT_OK,date即為setResult(RESULT_OK,intent);傳回的intent。

 

三、使用Intent廣播事件

1、最基本的廣播事件發送與接受:

廣播的發送,很簡單,產生一個Intent,設定Action,直接進行廣播:

 

public static final String BROAD_UI_STRING=com.example.intentbraodcast.BROAD_UI; 
Intent intent=new Intent(BROAD_UI_STRING);intent.putExtra(str, update ui by broadcast!);sendBroadcast(intent);

 

廣播的註冊,最好在廣播的發送前註冊廣播:

 

//註冊Broadcast Receiver     registerReceiver(new MyBroadcastReceiver, new IntentFilter(BROAD_UI_STRING));

 

註:上文中的 BROAD_UI_STRING就是一個自訂的獨一無二的字串,由於廣播不但可用於應用程式內部交換資料,還可用於系統間應用交換資料,故一般用傳統的包名首碼法來命名。

進行註冊以前,我們需要實現自己的接收器,繼承BroadcastReceiver即可,我們對廣播出的Intent繫結資料再次進行處理

 

public class MyBroadcastReceiver extends BroadcastReceiver {        @Override        public void onReceive(Context context, Intent intent) {           //TODO: React to the Intent received.        String actionString=intent.getAction();        if (actionString.equals(BROAD_UI_STRING))        {        //改變下一個activity中的值        String str=intent.getStringExtra(str);            Intent newIntent=new Intent();            newIntent.setClass(MainActivity.this,IntentActivity.class );            newIntent.putExtra(str, str);            context.startActivity(newIntent);        }        else if(actionString.equals(LOCAL_ACTION))        {        edittxt.setText(intent.getStringExtra(str));        }        }     }
廣播的登出:在我們不再廣播時,通常是介面掛起或停止時,需要對接收器進行登出:

 

 

 @Overrideprotected void onPause() { unregisterReceiver(receiver);super.onPause();}
需要注意的是,接收器中的處理常式需要在5秒鐘內完成,否則會顯示Force CLose的對話方塊。很多時候,我們希望當我們的應用程式在關閉時也能響應一些廣播,需要在Manifest中的application節點添加一個receiver標籤,指定接收器類名和過濾器標識符:

 

 

      
這樣,即使我們的應用程式處於關閉狀態也能響應廣播。

 

2、有序廣播

3、廣播Sticky Intent,在一些教程仍出現,但在android 5.0以後會漸漸廢棄,故不再討論。

4、LocalBroadcastManager(局部廣播管理器)

顧名思義,其用於局部資料的訊息驅動,是一種輕量級的handler,更高效的廣播模型。

操作過程與普通廣播管理器類似,只不過要先擷取LocalBroadcastManager:

 

lbm=LocalBroadcastManager.getInstance(MainActivity.this);
發送時將sendBroadcast改為lbm.sendBroadcast,註冊時將registerReceiver改為lbm.registerReceiver,登出時將unregisterReceiver改為lbm.unregisterReceiver

 

下面為樣本的全部代碼,工程檔案我也會放到最後:

 

package com.example.intentandbroadcast;import android.R.string;import android.app.Activity;import android.content.BroadcastReceiver;import android.content.Context;import android.content.Intent;import android.content.IntentFilter;import android.net.Uri;import android.os.Bundle;import android.support.v4.content.LocalBroadcastManager;import android.view.*;import android.view.View.OnClickListener;import android.widget.*;@SuppressWarnings(unused)public class MainActivity extends Activity { Button btn1; Button btn2,btn3,btn4,btn_broad_ui,btn_local_broad; EditText edittxt; TextView tv; LocalBroadcastManager lbm; MyBroadcastReceiver receiver; //定義intent識別碼 private static final int SHOW_SUBACTIVITY=1; private static final int PICK_CONTACT_SUBACTIVITY=2; public static final String BROAD_UI_STRING=com.example.intentbraodcast.BROAD_UI;  public static final String LOCAL_ACTION=com.example.intentbraodcast.LOCAL_ACTION;  void getviewdefinition() { btn1=(Button)findViewById(R.id.btn1);     btn2=(Button)findViewById(R.id.btn2);     btn3=(Button)findViewById(R.id.btn3);     btn4=(Button)findViewById(R.id.btn4);     btn_broad_ui=(Button)findViewById(R.id.btn_broad_ui);     edittxt=(EditText)findViewById(R.id.edittext);     tv=(TextView)findViewById(R.id.textview);     btn_local_broad=(Button)findViewById(R.id.btn_local_broad_ui);     lbm=LocalBroadcastManager.getInstance(MainActivity.this);    receiver=new MyBroadcastReceiver(); } public class OnButtonClick implements OnClickListener {@Overridepublic void onClick(View v) {// TODO Auto-generated method stubif(v==btn1){Intent intent=new Intent();intent.setClass(MainActivity.this, IntentActivity.class);//傳入識別碼唯一標識SHOW_SUBACTIVITY,啟動intent,以便擷取下一頁面返回的結果startActivityForResult(intent, SHOW_SUBACTIVITY);}else if(v==btn3){//觸發外部intent打電話Intent intent=new Intent(Intent.ACTION_DIAL,Uri.parse(tel:13237170570));startActivity(intent);}else if(v==btn4){//隱含選取連絡人,注意使用startActivity並不能啟動介面Intent intent=new Intent(Intent.ACTION_PICK,Uri.parse(content://contacts/people));startActivityForResult(intent,PICK_CONTACT_SUBACTIVITY);}else if(v==btn_broad_ui){Intent intent=new Intent(BROAD_UI_STRING);intent.putExtra(str, update ui by broadcast!);sendBroadcast(intent);}else if(v==btn_local_broad){//設定本地廣播,更高效:Intent intent=new Intent(LOCAL_ACTION);intent.putExtra(str, i am created by local broadcast!);lbm.sendBroadcast(intent);}}  }@Override    protected void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);       setContentView(R.layout.activity_main);        getviewdefinition();        OnButtonClick btnclick=new OnButtonClick();        btn1.setOnClickListener(btnclick);        btn3.setOnClickListener(btnclick);        btn4.setOnClickListener(btnclick);        btn_broad_ui.setOnClickListener(btnclick);        btn_local_broad.setOnClickListener(btnclick);    }@Overrideprotected void onResume() {// TODO Auto-generated method stubsuper.onResume();//註冊Broadcast Receiver     registerReceiver(receiver, new IntentFilter(BROAD_UI_STRING));     //註冊local broadcastlbm.registerReceiver(receiver, new IntentFilter(LOCAL_ACTION)); } @Overrideprotected void onPause() { unregisterReceiver(receiver); lbm.unregisterReceiver(receiver);super.onPause();}        @Overrideprotected void onActivityResult(int requestCode, int resultCode, Intent data) {// TODO Auto-generated method stub    super.onActivityResult(requestCode, resultCode, data);    if(requestCode==SHOW_SUBACTIVITY)    {    switch (resultCode) {    case RESULT_CANCELED:    {    Bundle bd=data.getExtras();    edittxt.setText(bd.getString(text));    break;    }    case RESULT_OK:    {    Bundle bd=data.getExtras();    edittxt.setText(bd.getString(text));    break;    }    default:    break;    }    }}          @Override    public boolean onCreateOptionsMenu(Menu menu) {        // Inflate the menu; this adds items to the action bar if it is present.        getMenuInflater().inflate(R.menu.main, menu);        return true;    }    @Override    public boolean onOptionsItemSelected(MenuItem item) {        // Handle action bar item clicks here. The action bar will        // automatically handle clicks on the Home/Up button, so long        // as you specify a parent activity in AndroidManifest.xml.        int id = item.getItemId();        if (id == R.id.action_settings) {            return true;        }        return super.onOptionsItemSelected(item);    }    public class MyBroadcastReceiver extends BroadcastReceiver {        @Override        public void onReceive(Context context, Intent intent) {           //TODO: React to the Intent received.        String actionString=intent.getAction();        if (actionString.equals(BROAD_UI_STRING))        {        //改變下一個activity中的值        String str=intent.getStringExtra(str);            Intent newIntent=new Intent();            newIntent.setClass(MainActivity.this,IntentActivity.class );            newIntent.putExtra(str, str);            context.startActivity(newIntent);        }        else if(actionString.equals(LOCAL_ACTION))        {        edittxt.setText(intent.getStringExtra(str));        }        }     }}

package com.example.intentandbroadcast;import java.security.PublicKey;import com.example.intentandbroadcast.MainActivity.MyBroadcastReceiver;import android.app.Activity;import android.app.PendingIntent.CanceledException;import android.content.BroadcastReceiver;import android.content.Context;import android.content.Intent;import android.content.IntentFilter;import android.os.Bundle;import android.support.v4.content.LocalBroadcastManager;import android.view.*;import android.view.View.OnClickListener;import android.widget.*;public class IntentActivity extends Activity {Button cancel,ok,btn_local;TextView txtintentTextView;IntentFilter filter;String stickystring;void getdefinition(){cancel=(Button)findViewById(R.id.resultcancel);        ok=(Button)findViewById(R.id.resultok);        btn_local=(Button)findViewById(R.id.btn_localintent);        txtintentTextView=(TextView)findViewById(R.id.textintent); }public class OnBtnClick implements OnClickListener{@Overridepublic void onClick(View v) {// TODO Auto-generated method stubswitch(v.getId()){case R.id.resultcancel:{Intent intent=new Intent();intent.setClass(IntentActivity.this, MainActivity.class);intent.putExtra(text, cancel:i am from intentactivity!and pass back me on childactivity finished!);setResult(RESULT_CANCELED,intent);finish();break;}case R.id.resultok:{Intent intent=new Intent(); intent.setClass(IntentActivity.this, MainActivity.class); intent.putExtra(text, ok: am from intentactivity!and pass back me on childactivity finished!); setResult(RESULT_OK,intent); finish(); break;}default:break;}}}    @Override    protected void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        //雷區,這個啟動的xml打錯了 調了好久        setContentView(R.layout.activity_intent);        getdefinition();//測試startactivyforresult        cancel.setOnClickListener(new OnBtnClick());        ok.setOnClickListener(new  OnBtnClick());    }@Override    public boolean onCreateOptionsMenu(Menu menu) {        // Inflate the menu; this adds items to the action bar if it is present.        getMenuInflater().inflate(R.menu.main, menu);        return true;    }    @Override    public boolean onOptionsItemSelected(MenuItem item) {        // Handle action bar item clicks here. The action bar will        // automatically handle clicks on the Home/Up button, so long        // as you specify a parent activity in AndroidManifest.xml.        int id = item.getItemId();        if (id == R.id.action_settings) {            return true;        }        return super.onOptionsItemSelected(item);    }    }

 



 

 



 

 

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.