為什麼Android要申請許可權
- 簡單說下在Android6.0及6.0以上一些google認為涉及“危險和使用者隱私”的一些許可權不僅要做清單檔案(android/app/src/AndroidMainfest.xml)裡面申請,還有單獨呼叫api,去讓使用者選擇是否同意你申請這個許可權。
- 例如:你想要你的app有讀寫手機外接記憶體卡許可權,那麼你需要在清單檔案裡面加下面兩行看字母應該懂的吧。但如果你的(android/app/build.gradle)裡的 android{defaultConfig {targetSdkVersion 23} } targetSdkVersion >= 23你需要動態去申請許可權,我發現react-native init app裡面的targetSdkVersion = 22這個,,,巧妙的躲過了,但有些手機系統是6.0或以上的手機targetSdkVersion 22是獲取不到有些許可權的,至少我知道的樂視就是無法逃脫,其他手機應該也有,而且這是一個android的安全機制,現在開發的app都應該儘量去遵守。
- 不多解釋了想了解可以search一下
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>複製程式碼
效果
前提
- (android/app/src/AndroidMainfest.xml) targetSdkVersion 改到 23或以上 ,為什麼要改????看上面
開始
- React-Native裡面有PermissionsAndroid去動態申請許可權,再說一句,動態申請同意一次就可以下次呼叫申請它不會再提醒使用者選擇了,如果拒絕了,可以再次申請,且在申請錢彈一個Dialog這個是手機系統的,我們只能提供一些解釋,下面用三個許可權來做解釋其實死是個。
1. 在 android/app/src/AndroidMainfest.xml 新增
<!--獲取讀寫外接儲存許可權-->
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
<!--獲取相機許可權-->
<uses-permission android:name="android.permission.CAMERA"/>
<!--獲取地址相關許可權-->
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/>複製程式碼
//新增 PermissionsAndroid RN自帶的
import { PermissionsAndroid } from 'react-native'複製程式碼
//給你們介紹下怎麼用它的方法
//返回 Promise型別 裡面是使用者是否授權的布林值
1. PermissionsAndroid.check(permission) //permission是String型
//返回String型別
'granted': 同意了
'denied' : 拒絕了
'never_ask_again' : 永久性拒絕下次再請求使用者也看不到了,尷不尷尬
2. PermissionsAndroid.request(permission, rationale?) //permission是String型,rationale物件
//返回一個物件
3. PermissionsAndroid.requestMultiple(permissions) //permissions為String型陣列
//就舉一個例子 記得加上async非同步
async requestReadPermission() {
try {
//返回string型別
const granted = await PermissionsAndroid.request(
PermissionsAndroid.PERMISSIONS.WRITE_EXTERNAL_STORAGE,
{
//第一次請求拒絕後提示使用者你為什麼要這個許可權
'title': '我要讀寫許可權',
'message': '沒許可權我不能工作,同意就好了'
}
)
if (granted === PermissionsAndroid.RESULTS.GRANTED) {
this.show("你已獲取了讀寫許可權")
} else {
this.show("獲取讀寫許可權失敗")
}
} catch (err) {
this.show(err.toString())
}
}
//核實
checkPermission() {
try {
//返回Promise型別
const granted = PermissionsAndroid.check(
PermissionsAndroid.PERMISSIONS.WRITE_EXTERNAL_STORAGE
)
granted.then((data)=>{
this.show("是否獲取讀寫許可權"+data)
}).catch((err)=>{
this.show(err.toString())
})
} catch (err) {
this.show(err.toString())
}
}
//請求多個
async requestMultiplePermission() {
try {
const permissions = [
PermissionsAndroid.PERMISSIONS.WRITE_EXTERNAL_STORAGE,
PermissionsAndroid.PERMISSIONS.ACCESS_FINE_LOCATION,
PermissionsAndroid.PERMISSIONS.CAMERA
]
//返回得是物件型別
const granteds = await PermissionsAndroid.requestMultiple(permissions)
var data = "是否同意地址許可權: "
if (granteds["android.permission.ACCESS_FINE_LOCATION"] === "granted") {
data = data + "是\n"
} else {
data = data + "否\n"
}
data = data+"是否同意相機許可權: "
if (granteds["android.permission.CAMERA"] === "granted") {
data = data + "是\n"
} else {
data = data + "否\n"
}
data = data+"是否同意儲存許可權: "
if (granteds["android.permission.WRITE_EXTERNAL_STORAGE"] === "granted") {
data = data + "是\n"
} else {
data = data + "否\n"
}
this.show(data)
} catch (err) {
this.show(err.toString())
}
}複製程式碼
import React,{Component} from 'react'
import {
StyleSheet,
View,
Text,
TouchableOpacity,
ToastAndroid,
PermissionsAndroid,
} from 'react-native'
export default class PermissionAndroidView extends Component {
render() {
return (
<View style={styles.container}>
<TouchableOpacity style={styles.button_view}
onPress={this.requestReadPermission.bind(this)}>
<Text style={styles.button_text}>申請讀寫許可權</Text>
</TouchableOpacity>
<TouchableOpacity style={styles.button_view}
onPress={this.requestCarmeraPermission.bind(this)}>
<Text style={styles.button_text}>申請相機許可權</Text>
</TouchableOpacity>
<TouchableOpacity style={styles.button_view}
onPress={this.requestLocationPermission.bind(this)}>
<Text style={styles.button_text}>申請訪問地址許可權</Text>
</TouchableOpacity>
<TouchableOpacity style={styles.button_view}
onPress={this.checkPermission.bind(this)}>
<Text style={styles.button_text}>查詢是否獲取了讀寫許可權</Text>
</TouchableOpacity>
<TouchableOpacity style={styles.button_view}
onPress={this.requestMultiplePermission.bind(this)}>
<Text style={styles.button_text}>一次申請所以許可權</Text>
</TouchableOpacity>
</View>
)
}
show(data) {
ToastAndroid.show(data,ToastAndroid.SHORT)
}
/*
* 彈出提示框向使用者請求某項許可權。返回一個promise,最終值為使用者是否同意了許可權申請的布林值。
* 其中rationale引數是可選的,其結構為包含title和message)的物件。
* 此方法會和系統協商,是彈出系統內建的許可權申請對話方塊,
* 還是顯示rationale中的資訊以向使用者進行解釋。
* */
async requestReadPermission() {
try {
//返回string型別
const granted = await PermissionsAndroid.request(
PermissionsAndroid.PERMISSIONS.WRITE_EXTERNAL_STORAGE,
{
//第一次請求拒絕後提示使用者你為什麼要這個許可權
'title': '我要讀寫許可權',
'message': '沒許可權我不能工作,同意就好了'
}
)
if (granted === PermissionsAndroid.RESULTS.GRANTED) {
this.show("你已獲取了讀寫許可權")
} else {
this.show("獲取讀寫許可權失敗")
}
} catch (err) {
this.show(err.toString())
}
}
async requestCarmeraPermission() {
try {
const granted = await PermissionsAndroid.request(
PermissionsAndroid.PERMISSIONS.CAMERA,
{
//第一次請求拒絕後提示使用者你為什麼要這個許可權
'title': '我要相機許可權',
'message': '沒許可權我不能工作,同意就好了'
}
)
if (granted === PermissionsAndroid.RESULTS.GRANTED) {
this.show("你已獲取了相機許可權")
} else {
this.show("獲取相機失敗")
}
} catch (err) {
this.show(err.toString())
}
}
async requestLocationPermission() {
try {
const granted = await PermissionsAndroid.request(
PermissionsAndroid.PERMISSIONS.ACCESS_FINE_LOCATION,
{
//第一次請求拒絕後提示使用者你為什麼要這個許可權
'title': '我要地址查詢許可權',
'message': '沒許可權我不能工作,同意就好了'
}
)
if (granted === PermissionsAndroid.RESULTS.GRANTED) {
this.show("你已獲取了地址查詢許可權")
} else {
this.show("獲取地址查詢失敗")
}
} catch (err) {
this.show(err.toString())
}
}
checkPermission() {
try {
//返回Promise型別
const granted = PermissionsAndroid.check(
PermissionsAndroid.PERMISSIONS.WRITE_EXTERNAL_STORAGE
)
granted.then((data)=>{
this.show("是否獲取讀寫許可權"+data)
}).catch((err)=>{
this.show(err.toString())
})
} catch (err) {
this.show(err.toString())
}
}
async requestMultiplePermission() {
try {
const permissions = [
PermissionsAndroid.PERMISSIONS.WRITE_EXTERNAL_STORAGE,
PermissionsAndroid.PERMISSIONS.ACCESS_FINE_LOCATION,
PermissionsAndroid.PERMISSIONS.CAMERA
]
//返回得是物件型別
const granteds = await PermissionsAndroid.requestMultiple(permissions)
var data = "是否同意地址許可權: "
if (granteds["android.permission.ACCESS_FINE_LOCATION"] === "granted") {
data = data + "是\n"
} else {
data = data + "否\n"
}
data = data+"是否同意相機許可權: "
if (granteds["android.permission.CAMERA"] === "granted") {
data = data + "是\n"
} else {
data = data + "否\n"
}
data = data+"是否同意儲存許可權: "
if (granteds["android.permission.WRITE_EXTERNAL_STORAGE"] === "granted") {
data = data + "是\n"
} else {
data = data + "否\n"
}
this.show(data)
} catch (err) {
this.show(err.toString())
}
}
}
const styles = StyleSheet.create({
container: {
flex: 1,
padding: 10,
},
button_view: {
margin:4,
borderRadius: 4,
backgroundColor: '#8d4dfc',
alignItems: 'center',
},
button_text: {
padding: 6,
fontSize: 16,
fontWeight: '600'
}
})
// 12點了再不睡,我就要猝死了,其實執行一下就知道什麼意思了複製程式碼
沒時間解釋了,直接可以執行看效果解釋的也很清楚