有很多操作,例如周期性的和服务器Sync(Email,Cloud Service),周期性的更新下载进度,等等是比较耗电的。因此可以根据电量,是否充电,Dock状态,网络连接状态这些条件来调整更新频率,以便节省电量。
和电池相关的几个Broadcast,都是battery manager发出的:
1, ACTION_BATTERY_CHANGED
这是个sticky broadcast,并且不能在manifest中注册receiver接收这个broadcast,因为是sticky的,所以app一启动就可以收到,相当于当前的电池状态。
IntentFilter ifilter = new IntentFilter(Intent.ACTION_BATTERY_CHANGED);
Intent batteryStatus = context.registerReceiver(null, ifilter); //因为是sticky broadcast,所以receiver使用null就可以。
这个broadcast中包含很多信息,例如是否在充电,是用USB充电还是AC充电
int status = batteryStatus.getIntExtra(BatteryManager.EXTRA_STATUS, -1);
boolean isCharging = status == BatteryManager.BATTERY_STATUS_CHARGING ||
status == BatteryManager.BATTERY_STATUS_FULL;
int chargePlug = batteryStatus.getIntExtra(BatteryManager.EXTRA_PLUGGED, -1);
boolean usbCharge = chargePlug == BatteryManager.BATTERY_PLUGGED_USB;
boolean acCharge = chargePlug == BatteryManager.BATTERY_PLUGGED_AC;
2,除了这个broadcast还可以接收其他一些broadcast,这些broadcast就可以在manifest中注册receiver接收了,相当于关注电池的变化。
<receiver android:name=".PowerConnectionReceiver">
<intent-filter>
<action android:name="android.intent.action.ACTION_POWER_CONNECTED"/> //充电器连接
<action android:name="android.intent.action.ACTION_POWER_DISCONNECTED"/> //充电器断开
</intent-filter>
</receiver>
<receiver android:name=".BatteryLevelReceiver">
<intent-filter>
<action android:name="android.intent.action.ACTION_BATTERY_LOW"/> //这两个用于电量的显著变化,一个是电量低,一个是不处于低电量状态了。
<action android:name="android.intent.action.ACTION_BATTERY_OKAY"/>
</intent-filter>
</receiver>
在receiver中不能处理太大的工作量,如果有大工作量要启动IntentService,而不要使用work thread。
和Dock相关的broadcast:
拿到Dock当前状态:
IntentFilter ifilter = new IntentFilter(Intent.ACTION_DOCK_EVENT);
Intent dockStatus = context.registerReceiver(null, ifilter);
后继Dock的变化:
也是接收ACTION_DOCK_EVENT
网络连接的状态
拿到当前连接状态
ConnectivityManager cm = (ConnectivityManager)context.getSystemService(Context.CONNECTIVITY_SERVICE);
NetworkInfo activeNetwork = cm.getActiveNetworkInfo();
boolean isConnected = activeNetwork != null && activeNetwork.isConnectedOrConnecting();
boolean isWiFi = activeNetwork.getType() == ConnectivityManager.TYPE_WIFI;
后继状态的变化
<action android:name="android.net.conn.CONNECTIVITY_CHANGE"/>
注册receiver时应该注意,在manifest中注册receiver可能导致app会被频繁唤醒,所以有些receiver需要动态注册,另外还可以通过package manager把manifest中注册的组件disable或者enable:
下面的code就是enable一个receiver:myReceiver
ComponentName receiver = new ComponentName(context, myReceiver.class);
PackageManager pm = context.getPackageManager();
pm.setComponentEnabledSetting(receiver,
PackageManager.COMPONENT_ENABLED_STATE_ENABLED,
PackageManager.DONT_KILL_APP)