普通權限沒有列出,因爲除了危險權限就是普通權限。
具體的危險權限組和權限如下:
-
CALENDAR
-
READ_CALENDAR
-
WRITE_CALENDAR
-
CAMERA
-
CAMERA
-
CONTACTS
-
READ_CONTACTS
-
WRITE_CONTACTS
-
GET_ACCOUNTS
-
LOCATION
-
ACCESS_FINE_LOCATION
-
ACCESS_COARSE_LOCATION
-
MICROPHONE
-
RECORD_AUDIO
-
PHONE
-
READ_PHONE_STATE
-
CALL_PHONE
-
READ_CALL_LOG
-
WRITE_CALL_LOG
-
ADD_VOICEMAIL
-
USE_SIP
-
PROCESS_OUTGOING_CALLS
-
SENSORS
-
BODY_SENSORS
-
SMS
-
SEND_SMS
-
RECEIVE_SMS
-
READ_SMS
-
RECEIVE_WAP_PUSH
-
RECEIVE_MMS
-
STORAGE
-
READ_EXTERNAL_STORAGE
-
WRITE_EXTERNAL_STORAGE
另外注意:表格中每一個危險權限都屬於一個權限組,我們在進行運行時權限處理時使用的是權限名,但是用戶一旦同一授權了,那麼該權限所對應的權限組中所有的其他權限也會同時被授權。
在運行時權限:
說白了用過智能手機的都知道,也就是在剛剛下載的App打開時,可能是照相,那麼系統將會詢問你是否授權攝像頭權限,打開相冊時是否允許訪問相冊,所以在這裏運行時的權限是很好理解的,不再解釋那麼多。
下面來新建一個項目RuntimePermissionTest項目。
這裏我們使用CALL_PHONE這個權限來作爲示例吧。
CALL_PHONE這個權限是編寫撥打電話功能的時候需要聲明的,因爲撥打電話會涉及用戶手機的資費問題,因而被列爲了危險權限。
先修改activity_main.xml佈局文件,如下所示:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
>
<Button
android:id="@+id/make_call"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="make Call"
/>
</LinearLayout>
當點擊按鈕時就去觸發撥打電話的邏輯。
修改MainActivity
public class MainActivity extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
Button makeCall = (Button) findViewById(R.id.make_call);
makeCall.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
//第一步就是判斷用戶是不是已經給過我們授權了,藉助的是ContextCompat.checkSelfPermission()方法。
//checkSelfPermission()方法接收兩個參數,第一個參數是Context,第二個參數是權限名。
//然後使用方法的返回值和PackageManager.PERMISSION_GRANTED作比較,相等就說明用戶已經授權。
if(ContextCompat.checkSelfPermission(MainActivity.this, Manifest.permission.CALL_PHONE)!= PackageManager.PERMISSION_GRANTED){
ActivityCompat.requestPermissions(MainActivity.this,new String[]{Manifest.permission.CALL_PHONE},1);
//如果沒有授權的話,則需要調用ActivityCompat.requestPermissions()方法來向用戶申請授權。
//requestPermissions接收三個參數,第一個參數要求是Activity的實例,第二個參數是一個String數組,我們要把申請的權限名放在數組中即可。
//第三個參數是請求碼,只要是唯一值就可以了。這裏傳入1.
}else{
call();
//如果授權的話,直接執行撥打電話的邏輯操作。
}
}
});
}
private void call(){
try{
Intent intent = new Intent(Intent.ACTION_CALL);
intent.setData(Uri.parse("tel:10086"));
startActivity(intent);
}catch (SecurityException e){
e.printStackTrace();
}
}
//調用完了requestPermissions()方法之後,系統會彈出一個權限申請的對話框,然後用戶可以選擇同意或者拒絕。
//不論是哪種結果,最終都會調到onRequestPermissionsResult()方法中,而授權的結果則會封裝在grantResults參數中。
@Override
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
switch(requestCode){
case 1:
//判斷最後的授權結果,如果用戶同意就調用call()方法來撥打電話。如果用戶拒絕的話我們只能放棄操作,並彈出一條失敗提示。
if (grantResults.length > 0 &&grantResults[0] == PackageManager.PERMISSION_GRANTED){
call();
}else{
Toast.makeText(this, "You denied the permission", Toast.LENGTH_SHORT).show();
}
break;
default:
}
}
}