閱讀161 返回首頁    go 阿裏雲 go 技術社區[雲棲]


Android開發22——廣播接收者BroadcastReceiver的原理和注冊方式


一、廣播機製的基本概念

當某個事件產生時(如一條短信發來或一個電話打來),android操作係統會把這個事件廣播給所有注冊的廣播接收者,需要處理這個事件的廣播接收者進行處理。其實這就是日常生活中的廣播。發生一個新聞後,廣播電台會廣播這個新聞給打開收音機的人,對這個新聞感興趣的人會關注,可能會拿筆記下。新聞就是事件,廣播電台就是android係統,打開收音機的人就是廣播接收者,感興趣的人就是需要處理該事件的廣播接收者,拿筆記下就是對該事件進行的操作。

 


二、廣播的分類——普通廣播和有序廣播

①普通廣播:完全異步,邏輯上可以被任何廣播接收者接收到。優點是效率較高。缺點是一個接收者不能將處理結果傳遞給下一個接收者,並無法終止廣播intent的傳播。


②有序廣播:按照被接收者的優先級順序,在被接收者中一次傳播。比如有三個廣播接收者A,B,C,優先級是A > B > C。那這個消息先傳給A,再傳給B,最後傳給C。每個接收者有權中終止廣播,比如B終止廣播,C就無法接收到。此外A接收到廣播後可以對結果對象進行操作,當廣播傳給B時,B可以從結果對象中取得A存入的數據。如係統收到短信發出的廣播就是有序廣播。

 


三、注冊廣播接收者的兩種方式

①在AndroidManifest.xml中注冊

在配置文件中注冊的接收者的特點是即使應用程序已被關閉,該接收者依然可接受它感興趣的廣播,比如手機電池電量的廣播接收者,沒有必要將某個程序開啟。下麵的例子1、2廣播接收者會接收到撥打電話的廣播。

    <application android:icon="@drawable/icon" android:label="@string/app_name">
        <activity android:name=".MainActivity"
                  android:label="@string/app_name">
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />
                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
        
        	<!-- 廣播接收者1-->
		<receiver android:name=".BroadcastReceiver1">
			<intent-filter>
				<action android:name="android.intent.action.CALL"></action>
			</intent-filter>
		</receiver>
		
		<!-- 廣播接收者2 -->
		<receiver android:name=".BroadcastReceiver2">
			<intent-filter>
				<action android:name="android.intent.action.CALL"></action>
			</intent-filter>
		</receiver>
		
		<!-- 廣播接收者3 -->
		<receiver android:name=".BroadcastReceiver3">
			<intent-filter>
				<action android:name="android.intent.action.PICK"></action>
			</intent-filter>
		</receiver>
		
    </application>
/**
 * 模擬撥打電話廣播
 * 
 * @author 徐越
 * 
 */
public class MainActivity extends Activity
{

	@Override
	public void onCreate(Bundle savedInstanceState)
	{
		super.onCreate(savedInstanceState);
		setContentView(R.layout.main);
		Intent intent = new Intent();
		intent.setAction("android.intent.action.CALL");
		this.sendBroadcast(intent);
	}
}

/**
 * 每次接收廣播都會生成新的BroadcastReceiver1,當處理完onReceive方法後就不會再被使用
 * 再次接收就在生成新的BroadcastReceiver1對象
 * 
 * @author 徐越
 * 
 */
public class BroadcastReceiver1 extends android.content.BroadcastReceiver
{
	public BroadcastReceiver1()
	{
		Log.i("xy_Receiver", "construtor1");
	}

	@Override
	public void onReceive(Context context, Intent intent)
	{
		Log.i("xy_Receiver", "onReceive1");
	}

}

/**
 * 廣播接收者2
 * 
 * @author 徐越
 * 
 */
public class BroadcastReceiver2 extends android.content.BroadcastReceiver
{
	public BroadcastReceiver2()
	{
		Log.i("xy_Receiver", "construtor2");
	}

	@Override
	public void onReceive(Context context, Intent intent)
	{
		Log.i("xy_Receiver", "onReceive2");
	}

}

/**
 * 廣播接收者3
 * 
 * @author 徐越
 * 
 */
public class BroadcastReceiver3 extends android.content.BroadcastReceiver
{

	public BroadcastReceiver3()
	{
		Log.i("xy_Receiver", "construtor3");
	}

	@Override
	public void onReceive(Context context, Intent intent)
	{
		Log.i("xy_Receiver", "onReceive3");
	}

}

②在Activity中注冊

在Activity中綁定接收者必須依附該應用程序存在,或者一個BroadcastReceiver用於更新UI,就沒有必要再程序關閉時接收者還運行,故無需在AndroidManifest.xml中注冊而可以放在Activity中注冊。

/**
 * Activity中注冊廣播接收者
 * 
 * @author 徐越
 * 
 */
public class MainActivity extends Activity
{
	private BroadcastReceiver receiver;
	private static final String CALL_ACTION = "android.intent.action.CALL";

	@Override
	public void onCreate(Bundle savedInstanceState)
	{
		super.onCreate(savedInstanceState);
		setContentView(R.layout.main);
	}

	/**
	 * 模擬發送一個電話的廣播
	 * 
	 * @param v
	 */
	public void sendBroadCast(View v)
	{
		Intent intent = new Intent();
		intent.setAction("android.intent.action.CALL");
		this.sendBroadcast(intent);
	}

	public void bindReceiver(View v)
	{
		receiver = new BroadcastReceiver();
		IntentFilter intentFilter = new IntentFilter();
		intentFilter.addAction(CALL_ACTION);
		this.registerReceiver(receiver, intentFilter);
	}

	public void unBindReceiver(View v)
	{
		this.unregisterReceiver(receiver);
	}
}

public class BroadcastReceiver extends android.content.BroadcastReceiver
{

	@Override
	public void onReceive(Context context, Intent intent)
	{
		Log.i("xy", "receiver");
	}

}


 

 


最後更新:2017-04-04 07:03:09

  上一篇:go 2013年科技10大看點:蘋果之變
  下一篇:go 瑞典一男子賣含病毒軟件被判4年