Android 系統級別的Service有好多,可以通過getSystemService(@ServiceName @NonNull String name)方法得到(通過@Service注解限定參數范圍)。
系統Service主要有:
- WINDOW_SERVICE(android.view.WindowManager)
- LAYOUT_INFLATER_SERVICE(android.view.LayoutInflater)
- ACTIVITY_SERVICE(android.app.ActivityManager)
- POWER_SERVICE(android.os.PowerManager)
- ALARM_SERVICE(android.app.AlarmManager)
- NOTIFICATION_SERVICE(android.app.NotificationManager)
- KEYGUARD_SERVICE(android.app.KeyguardManager)
- LOCATION_SERVICE(android.location.LocationManager)
- SEARCH_SERVICE(android.app.SearchManager)
- SENSOR_SERVICE(android.hardware.SensorManager)
- STORAGE_SERVICE(android.os.storage.StorageManager)
- VIBRATOR_SERVICE(android.os.Vibrator)
- CONNECTIVITY_SERVICE(android.net.ConnectivityManager)
- WIFI_SERVICE(android.net.wifi.WifiManager)
- AUDIO_SERVICE(android.media.AudioManager)
- MEDIA_ROUTER_SERVICE(android.media.MediaRouter)
- TELEPHONY_SERVICE(android.telephony.TelephonyManager)
- TELEPHONY_SUBSCRIPTION_SERVICE(android.telephony.SubscriptionManager)
- CARRIER_CONFIG_SERVICE(android.telephony.CarrierConfigManager)
- INPUT_METHOD_SERVICE(android.view.inputmethod.InputMethodManager)
- UI_MODE_SERVICE(android.app.UiModeManager)
- DOWNLOAD_SERVICE(android.app.DownloadManager)
- BATTERY_SERVICE(android.os.BatteryManager)
- JOB_SCHEDULER_SERVICE(android.app.job.JobScheduler)
- NETWORK_STATS_SERVICE(android.app.usage.NetworkStatsManager)
- HARDWARE_PROPERTIES_SERVICE(android.os.HardwarePropertiesManager)
WindowManager
經常看直播的小伙伴們會發現現在退出直播頁之后會有一個懸浮窗在直播列表上,方便用戶在查看其它直播的時候仍然可以看到之前的直播內容,這個通過WindowManager就可以實現。WindowManager繼承自ViewManager,ViewManager里邊有添加刪除更新View的方法
public void addView(View view, ViewGroup.LayoutParams params);
public void updateViewLayout(View view, ViewGroup.LayoutParams params);
public void removeView(View view);
其中LayoutParams中可以定義View的坐標,type(window類型),flag(顯示特性),softInputMode,gravity,horizontalMargin,verticalMargin,format,windowAnimations(系統資源),alpha等屬性。只要在調用這三個方法就可以了。
LayoutInflater
LayoutInflater比較常用,尤其在Adapter中經常會用到
LayoutInflater.from(context).inflate(R.layout.item, parent, false)
這里注意一下后兩個參數,parent一般不推薦傳null,如果上邊這種形式返回的是實例化出來的View,如果false改為true,返回的為第二個參數parent,這點可以從源碼中得到答案。
// We are supposed to attach all the views we found (int temp)
// to root. Do that now.
if (root != null && attachToRoot) {
root.addView(temp, params);
}
// Decide whether to return the root that was passed in or the
// top view found in xml.
if (root == null || !attachToRoot) {
result = temp;
}
root為傳進來的parent,result開始初始化為root,最后返回result。
ActivityManager
ActivityManager的很多方法是通過ActivityManagerNative實現的,ActivityManagerNative繼承了Binder并實現了IActivityManager接口。ActivityManager里常用方法:
//跟當前app有關系的任務列表
public List<ActivityManager.AppTask> getAppTasks()
//當前運行的Service列表
public List<RunningServiceInfo> getRunningServices(int maxNum) throws SecurityException
//得到內存信息
public void getMemoryInfo(MemoryInfo outInfo)
//設備配置信息
public ConfigurationInfo getDeviceConfigurationInfo()
//獲取系統運行進程
public List<RunningAppProcessInfo> getRunningAppProcesses()
AlarmManager
AlarmManager 可以在未來的一個時間點調起app,到了時間點是如果app沒有啟動,系統會廣播之前設定的Intent,自動啟動app。
AlarmManager常用方法
/** @param type {ELAPSED_REALTIME}, {ELAPSED_REALTIME_WAKEUP},
* {RTC}, {RTC_WAKEUP}中的一個,喚醒方式.
* @param triggerAtMillis 設定的時間點,type方式不同,表示的時間不同
* @param operation執行的Intent.
public void set(int type, long triggerAtMillis, PendingIntent operation)
//重復Alarm,intervallMillis表示兩次的間隔
public void setRepeating(int type, long triggerAtMillis, long intervalMillis, PendingIntent operation)
//API 19開始上邊兩個方法設定的時間變得不準確,系統添加了下邊兩個方法保證嚴格傳遞。
public void setWindow(int type, long windowStartMillis, long windowLengthMillis, PendingIntent operation)
public void setExact(int type, long triggerAtMillis, PendingIntent operation)
設置完之后要在工程內創建接受Intent的Activity、Broadcast或者Service處理邏輯。
NotificationManager
NotificationManager比較常見,用來發送消息通知.
notifyManager = (NotificationManager)context.getSystemService(Context.NOTIFICATION_SERVICE);
builder = new Notification.Builder(context);
builder.setContentTitle(context.getString(R.string.offline_package_download, mission.getName()))
.setContentText(context.getString(R.string.start_download))
.setSmallIcon(android.R.drawable.stat_sys_download).setProgress(100, 0, true)
.setTicker(context.getString(R.string.start_download)).setAutoCancel(true);
notifyManager.notify(missionId, builder.getNotification());
LocationManager
提供設備地理位置信息的Service。
LocationManager manager = (LocationManager)getSystemService(LOCATION_SERVICE);
//需要確認權限ACCESS_COARSE_LOCATION, ACCESS_FINE_LOCATION一個粗精度,一個精確精度,至少一個
manager.requestLocationUpdates(LocationManager.GPS_PROVIDER, 1000, 50.0f, new LocationListener() {
@Override
public void onLocationChanged(Location location) {
}
@Override
public void onStatusChanged(String provider, int status, Bundle extras) {
}
@Override
public void onProviderEnabled(String provider) {
}
@Override
public void onProviderDisabled(String provider) {
}
});
另外,LocationManager里邊還可以獲取并設置GPS、NetWork等提供獲取位置的方式,這里不在贅述。
SearchManager
實際開發中,并不需要直接與SearchManager交互,因為Activity和Intent(ACTION_SEARCH) 中已經提供了搜索的方法。
SensorManager
使用SensorManager時要注意傳感器的釋放,避免耗電,鎖屏時系統會自動釋放傳感器。
public class SensorActivity extends Activity implements SensorEventListener {
private final SensorManager mSensorManager;
private final Sensor mAccelerometer;
public SensorActivity() {
mSensorManager = (SensorManager)getSystemService(SENSOR_SERVICE);
mAccelerometer = mSensorManager.getDefaultSensor(Sensor.TYPE_ACCELEROMETER);
}
protected void onResume() {
super.onResume();
mSensorManager.registerListener(this, mAccelerometer, SensorManager.SENSOR_DELAY_NORMAL);
}
protected void onPause() {
super.onPause();
mSensorManager.unregisterListener(this);
}
public void onAccuracyChanged(Sensor sensor, int accuracy) {
}
public void onSensorChanged(SensorEvent event) {
}
}
Vibrator
需要權限:android.Manifest.permission#VIBRATE
Vibrator使用起來比較簡單,兩個常用方法:
//振動milliseconds毫秒
public void vibrate(long milliseconds)
//pattern控制振動的開關,數組內第一個元素表示等待多長時間開始振動,第二個元素表示振動多長時間,依次類推。repeat表示從數組內開始重復振動的索引,傳-1表示不重復。
public void vibrate(long[] pattern, int repeat)
//停止振動
public abstract void cancel();
ConnectivityManager
ConnectivityManager提供網絡連接狀態查詢,并在網絡狀態改變時通知App。
主要作用:
- 監聽網絡連接(Wi-fi,GPRS,UMTS,等)
- 網絡連接改變時發送廣播
- 網絡丟失時試圖故障轉移到另一個網絡
- 提供查詢大致或精確可用網絡狀態的API
- 提供查詢并選定數據傳輸網絡的API
//網絡是否可用
ConnectivityManager conManager = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE);
NetworkInfo networkInfo = conManager.getActiveNetworkInfo();
return (networkInfo != null && networkInfo.isConnected());
//判斷Wifi狀態
ConnectivityManager manager = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE);
return manager.getActiveNetworkInfo().getType() == ConnectivityManager.TYPE_WIFI;
//注冊廣播,接受網絡狀態變化,
IntentFilter filter = new IntentFilter(ConnectivityManager.CONNECTIVITY_ACTION);
registerReceiver(NetworkReceiver, filter);
WifiManager
WifiManager管理各種Wi-fi連接,提供打開、關閉Wi-fi,連接、斷開連接、添加網絡,瀏覽接入點,獲取連接網絡信息的API。通過Context.getSystemService(Context.WIFI_SERVICE)獲取實例時應該使用application context,避免內存泄漏。
AudioManager
AudioManager管理音量和鈴聲模式。
//獲取鈴聲模式AudioManager.RINGER_MODE_NORMAL、AudioManager.RINGER_MODE_SILENT、AudioManager.RINGER_MODE_VIBRATE
public int getRingerMode()
//設置鈴聲模式
public void setRingerMode(int ringerMode)
//獲取流最大音量
public int getStreamMaxVolume(int streamType)
//獲取流最小音量
public int getStreamMinVolume(int streamType)
//獲取流當前音量
public int getStreamVolume(int streamType)
//調整最相關的流的音量
//direction ADJUST_LOWER、ADJUST_RAISE、ADJUST_SAME、ADJUST_MUTE、ADJUST_UNMUTE
public void adjustVolume(int direction, int flags)
//設備音量是否鎖定
public boolean isVolumeFixed()
TelephonyManager
通過TelephonyManager可以獲取手機卡、運營商、當前網絡、國家代碼等信息。
TelephonyManager manager = (TelephonyManager) getSystemService(TELEPHONY_SERVICE);
Log.e("getDeviceId",manager.getDeviceId());//deviceID
Log.e("getNetworkOperatorName",manager.getNetworkOperatorName());//運營商名稱
Log.e("isNetworkRoaming",manager.isNetworkRoaming()+"");//是否漫游
Log.e("getNetworkCountryIso",manager.getNetworkCountryIso());//國家代碼
Log.e("getNetworkType",manager.getNetworkType()+"");//當前網絡類型,2G\3G\4G
Log.e("getSimState",manager.getSimState()+"");//默認SIM卡狀態
Log.e("getSimOperator",manager.getSimOperator());//SIM卡經營者
Log.e("getSimOperatorName",manager.getSimOperatorName());//SIM卡經營者名稱
Log.e("getSimCountryIso",manager.getSimCountryIso());//SIM卡經營者所在國家代碼
Log.e("getSimSerialNumber",manager.getSimSerialNumber());//SIM卡序列號
Log.e("getLine1Number",manager.getLine1Number());//手機號
... ...
InputMethodManager
InputMethodManager用來管理軟鍵盤。常用方法包括hide,show,toggle.
InputMethodManager manager = (InputMethodManager) getSystemService(INPUT_METHOD_SERVICE);
switch (view.getId()) {
case R.id.hide:
//隱藏軟鍵盤
manager.hideSoftInputFromWindow(editText.getWindowToken(), InputMethodManager.HIDE_IMPLICIT_ONLY);
break;
case R.id.show:
//顯示選擇輸入法懸浮窗
manager.showInputMethodPicker();
//顯示軟鍵盤
manager.showSoftInput(editText, InputMethodManager.SHOW_IMPLICIT);
break;
case R.id.toggle:
//軟鍵盤開關
manager.toggleSoftInputFromWindow(editText.getWindowToken(), InputMethodManager.SHOW_IMPLICIT, InputMethodManager.HIDE_IMPLICIT_ONLY);
break;
}
UiModeManager
UiModeManager管理設備夜間模式和車載模式,常用方法:
UiModeManager manager = (UiModeManager) getSystemService(UI_MODE_SERVICE);
switch (view.getId()){
case R.id.car_mode_yes:
// 開啟車載模式
manager.enableCarMode(0);
break;
case R.id.car_mode_no:
// 關閉車載模式
manager.disableCarMode(0);
break;
case R.id.night_mode_yes:
// 開啟夜間模式,注意setNightMode只有在開啟車載模式時才起作用
manager.setNightMode(UiModeManager.MODE_NIGHT_YES);
Log.e(TAG, String.valueOf(manager.getNightMode()));
break;
case R.id.night_mode_no:
// 關閉夜間模式
manager.setNightMode(UiModeManager.MODE_NIGHT_YES);
Log.e(TAG, String.valueOf(manager.getNightMode()));
break;
}
((Button)view).setText(String.valueOf(manager.getCurrentModeType()));
DownloadManager
DownloadManager用于處理下載長時間下載操作。DownloadManager會在后臺下載,監聽HTTP連接并在下載失敗或者系統重啟或者連接變化是重新下載。請求下載是應該注冊broadcast receiver處理Notification點擊和下載完成后的操作。
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_download_manager);
IntentFilter filter = new IntentFilter(DownloadManager.ACTION_DOWNLOAD_COMPLETE);
BroadcastReceiver receiver = new BroadcastReceiver() {
@Override
public void onReceive(Context context, Intent intent) {
// reference對應startDownload中manger.enqueue的返回值。
long reference = intent.getLongExtra(DownloadManager.EXTRA_DOWNLOAD_ID, -1);
Log.e(TAG, "onReceive: "+reference);
}
};
registerReceiver(receiver, filter);
}
public void onClick(View view){
switch (view.getId()){
case R.id.download_start:
startDownload();
break;
}
}
private void startDownload() {
DownloadManager manager = (DownloadManager) getSystemService(DOWNLOAD_SERVICE);
DownloadManager.Request down = new DownloadManager.Request(Uri.parse(PATH));
down.setDescription("test test");
down.setNotificationVisibility(DownloadManager.Request.VISIBILITY_VISIBLE_NOTIFY_COMPLETED);
down.setDestinationInExternalFilesDir(this, Environment.DIRECTORY_MOVIES,"test.mp4");
long l = manager.enqueue(down);
Log.e(TAG, "startDownload: "+l);
}
BatteryManager
BatteryManager包涵了ACTION_BATTERY_CHANGED這個Intent的常量和字符串,提供了查詢電量和充電屬性的API。
IntentFilter filter = new IntentFilter(Intent.ACTION_BATTERY_CHANGED);
Intent batteryStatus = context.registerReceiver(null, filter);
//你可以讀到充電狀態,如果在充電,可以讀到是usb還是交流電
// 是否在充電
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;
另外除去上述常見Service之外還有PowerManager、KeyguardManager、StorageManager、MediaRouter、SubscriptionManager、CarrierConfigManager、JobScheduler、NetworkStatsManager、HardwarePropertiesManager后續補全。