Nil*_*bja 151 android android-permissions android-6.0-marshmallow
我目前正在开发一个需要几个"危险"权限的应用程序.因此,我尝试在Android Marshmallow(API级别23)中添加"请求许可",但无法找到如何执行此操作.
如何在我的应用中使用新的权限模型请求权限?
小智 219
使用以下代码打开对话框:
ActivityCompat.requestPermissions(MainActivity.this,
new String[]{Manifest.permission.READ_EXTERNAL_STORAGE},
1);
Run Code Online (Sandbox Code Playgroud)
获取活动结果如下:
@Override
public void onRequestPermissionsResult(int requestCode,
String permissions[], int[] grantResults) {
switch (requestCode) {
case 1: {
// If request is cancelled, the result arrays are empty.
if (grantResults.length > 0
&& grantResults[0] == PackageManager.PERMISSION_GRANTED) {
// permission was granted, yay! Do the
// contacts-related task you need to do.
} else {
// permission denied, boo! Disable the
// functionality that depends on this permission.
Toast.makeText(MainActivity.this, "Permission denied to read your External storage", Toast.LENGTH_SHORT).show();
}
return;
}
// other 'case' lines to check for other
// permissions this app might request
}
}
Run Code Online (Sandbox Code Playgroud)
更多信息:https://developer.android.com/training/permissions/requesting.html
Tar*_*run 56
这个结构我用来检查我的应用程序是否有权限,而不是请求它是否没有权限.所以在我想要检查的主代码中写下面的内容:
int MyVersion = Build.VERSION.SDK_INT;
if (MyVersion > Build.VERSION_CODES.LOLLIPOP_MR1) {
if (!checkIfAlreadyhavePermission()) {
requestForSpecificPermission();
}
}
Run Code Online (Sandbox Code Playgroud)
模块checkIfAlreadyhavePermission()实现为:
private boolean checkIfAlreadyhavePermission() {
int result = ContextCompat.checkSelfPermission(this, Manifest.permission.GET_ACCOUNTS);
if (result == PackageManager.PERMISSION_GRANTED) {
return true;
} else {
return false;
}
}
Run Code Online (Sandbox Code Playgroud)
模块requestForSpecificPermission()实现为:
private void requestForSpecificPermission() {
ActivityCompat.requestPermissions(this, new String[]{Manifest.permission.GET_ACCOUNTS, Manifest.permission.RECEIVE_SMS, Manifest.permission.READ_SMS, Manifest.permission.READ_EXTERNAL_STORAGE, Manifest.permission.WRITE_EXTERNAL_STORAGE}, 101);
}
Run Code Online (Sandbox Code Playgroud)
并在活动中覆盖:
@Override
public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {
switch (requestCode) {
case 101:
if (grantResults[0] == PackageManager.PERMISSION_GRANTED) {
//granted
} else {
//not granted
}
break;
default:
super.onRequestPermissionsResult(requestCode, permissions, grantResults);
}
}
Run Code Online (Sandbox Code Playgroud)
有关更多详细信息,请参阅此链接:http://revisitingandroid.blogspot.in/2017/01/how-to-check-and-request-for-run-time.html
Far*_*han 18
我使用了谷歌开发人员编写的这个包装器(推荐).它超级好用.
https://github.com/googlesamples/easypermissions
处理检查并在需要时请求许可的功能
public void locationAndContactsTask() {
String[] perms = { Manifest.permission.ACCESS_FINE_LOCATION, Manifest.permission.READ_CONTACTS };
if (EasyPermissions.hasPermissions(this, perms)) {
// Have permissions, do the thing!
Toast.makeText(this, "TODO: Location and Contacts things", Toast.LENGTH_LONG).show();
} else {
// Ask for both permissions
EasyPermissions.requestPermissions(this, getString(R.string.rationale_location_contacts),
RC_LOCATION_CONTACTS_PERM, perms);
}
}
Run Code Online (Sandbox Code Playgroud)
快乐编码:)
小智 15
从Android Marshmallow开始,我们需要向用户请求特定权限.如果已经给出了许可,我们也可以通过代码查看.以下是常用权限列表:
android.permission-group.CALENDAR
- android.permission.READ_CALENDAR
- android.permission.WRITE_CALENDAR
android.permission-group.CAMERA
- android.permission.CAMERA
android.permission-group.CONTACTS
- android.permission.READ_CONTACTS
- android.permission.WRITE_CONTACTS
- android.permission.GET_ACCOUNTS
android.permission-group.LOCATION
- android.permission.ACCESS_FINE_LOCATION
- android.permission.ACCESS_COARSE_LOCATION
android.permission-group.MICROPHONE
- android.permission.RECORD_AUDIO
android.permission-group.PHONE
- android.permission.READ_PHONE_STATE
- android.permission.CALL_PHONE
- android.permission.READ_CALL_LOG
- android.permission.WRITE_CALL_LOG
- android.permission.ADD_VOICEMAIL
- android.permission.USE_SIP
- android.permission.PROCESS_OUTGOING_CALLS
android.permission-group.SENSORS
- android.permission.BODY_SENSORS
android.permission-group.SMS
- android.permission.SEND_SMS
- android.permission.RECEIVE_SMS
- android.permission.READ_SMS
- android.permission.RECEIVE_WAP_PUSH
- android.permission.RECEIVE_MMS
- android.permission.READ_CELL_BROADCASTS
android.permission-group.STORAGE
- android.permission.READ_EXTERNAL_STORAGE
- android.permission.WRITE_EXTERNAL_STORAGE
以下是检查权限的示例代码:
if (ContextCompat.checkSelfPermission(context, Manifest.permission.WRITE_CALENDAR) != PackageManager.PERMISSION_GRANTED) {
if (ActivityCompat.shouldShowRequestPermissionRationale((Activity) context, Manifest.permission.WRITE_CALENDAR)) {
AlertDialog.Builder alertBuilder = new AlertDialog.Builder(context);
alertBuilder.setCancelable(true);
alertBuilder.setMessage("Write calendar permission is necessary to write event!!!");
alertBuilder.setPositiveButton(android.R.string.yes, new DialogInterface.OnClickListener() {
@TargetApi(Build.VERSION_CODES.JELLY_BEAN)
public void onClick(DialogInterface dialog, int which) {
ActivityCompat.requestPermissions((Activity)context, new String[]{Manifest.permission.WRITE_CALENDAR}, MY_PERMISSIONS_REQUEST_WRITE_CALENDAR);
}
});
} else {
ActivityCompat.requestPermissions((Activity)context, new String[]{Manifest.permission.WRITE_CALENDAR}, MY_PERMISSIONS_REQUEST_WRITE_CALENDAR);
}
}
Run Code Online (Sandbox Code Playgroud)
Pha*_*inh 13
我在类的请求运行的权限Activity或Fragment
它还可以帮助您显示基本原理或打开设置以在用户拒绝权限(有/无Never ask again)选项后更轻松地启用权限
class RequestPermissionHandler(private val activity: Activity? = null,
private val fragment: Fragment? = null,
private val permissions: Set<String> = hashSetOf(),
private val listener: Listener? = null
) {
private var hadShowRationale: Boolean = false
fun requestPermission() {
hadShowRationale = showRationaleIfNeed()
if (!hadShowRationale) {
doRequestPermission(permissions)
}
}
fun retryRequestDeniedPermission() {
doRequestPermission(permissions)
}
private fun showRationaleIfNeed(): Boolean {
val unGrantedPermissions = getPermission(permissions, Status.UN_GRANTED)
val permanentDeniedPermissions = getPermission(unGrantedPermissions, Status.PERMANENT_DENIED)
if (permanentDeniedPermissions.isNotEmpty()) {
val consume = listener?.onShowSettingRationale(unGrantedPermissions)
if (consume != null && consume) {
return true
}
}
val temporaryDeniedPermissions = getPermission(unGrantedPermissions, Status.TEMPORARY_DENIED)
if (temporaryDeniedPermissions.isNotEmpty()) {
val consume = listener?.onShowPermissionRationale(temporaryDeniedPermissions)
if (consume != null && consume) {
return true
}
}
return false
}
fun requestPermissionInSetting() {
val intent = Intent(Settings.ACTION_APPLICATION_DETAILS_SETTINGS)
val packageName = activity?.packageName ?: run {
fragment?.requireActivity()?.packageName
}
val uri = Uri.fromParts("package", packageName, null)
intent.data = uri
activity?.apply {
startActivityForResult(intent, REQUEST_CODE)
} ?: run {
fragment?.startActivityForResult(intent, REQUEST_CODE)
}
}
fun onRequestPermissionsResult(requestCode: Int, permissions: Array<String>,
grantResults: IntArray) {
if (requestCode == REQUEST_CODE) {
for (i in grantResults.indices) {
if (grantResults[i] == PackageManager.PERMISSION_GRANTED) {
markNeverAskAgainPermission(permissions[i], false)
} else if (!shouldShowRequestPermissionRationale(permissions[i])) {
markNeverAskAgainPermission(permissions[i], true)
}
}
var hasShowRationale = false
if (!hadShowRationale) {
hasShowRationale = showRationaleIfNeed()
}
if (hadShowRationale || !hasShowRationale) {
notifyComplete()
}
}
}
fun onActivityResult(requestCode: Int) {
if (requestCode == REQUEST_CODE) {
getPermission(permissions, Status.GRANTED).forEach {
markNeverAskAgainPermission(it, false)
}
notifyComplete()
}
}
fun cancel() {
notifyComplete()
}
private fun doRequestPermission(permissions: Set<String>) {
activity?.let {
ActivityCompat.requestPermissions(it, permissions.toTypedArray(), REQUEST_CODE)
} ?: run {
fragment?.requestPermissions(permissions.toTypedArray(), REQUEST_CODE)
}
}
private fun getPermission(permissions: Set<String>, status: Status): Set<String> {
val targetPermissions = HashSet<String>()
for (p in permissions) {
when (status) {
Status.GRANTED -> {
if (isPermissionGranted(p)) {
targetPermissions.add(p)
}
}
Status.TEMPORARY_DENIED -> {
if (shouldShowRequestPermissionRationale(p)) {
targetPermissions.add(p)
}
}
Status.PERMANENT_DENIED -> {
if (isNeverAskAgainPermission(p)) {
targetPermissions.add(p)
}
}
Status.UN_GRANTED -> {
if (!isPermissionGranted(p)) {
targetPermissions.add(p)
}
}
}
}
return targetPermissions
}
private fun isPermissionGranted(permission: String): Boolean {
return activity?.let {
ActivityCompat.checkSelfPermission(it, permission) == PackageManager.PERMISSION_GRANTED
} ?: run {
ActivityCompat.checkSelfPermission(fragment!!.requireActivity(), permission) == PackageManager.PERMISSION_GRANTED
}
}
private fun shouldShowRequestPermissionRationale(permission: String): Boolean {
return activity?.let {
ActivityCompat.shouldShowRequestPermissionRationale(it, permission)
} ?: run {
ActivityCompat.shouldShowRequestPermissionRationale(fragment!!.requireActivity(), permission)
}
}
private fun notifyComplete() {
listener?.onComplete(getPermission(permissions, Status.GRANTED), getPermission(permissions, Status.UN_GRANTED))
}
private fun getPrefs(context: Context): SharedPreferences {
return context.getSharedPreferences("SHARED_PREFS_RUNTIME_PERMISSION", Context.MODE_PRIVATE)
}
private fun isNeverAskAgainPermission(permission: String): Boolean {
return getPrefs(requireContext()).getBoolean(permission, false)
}
private fun markNeverAskAgainPermission(permission: String, value: Boolean) {
getPrefs(requireContext()).edit().putBoolean(permission, value).apply()
}
private fun requireContext(): Context {
return fragment?.requireContext() ?: run {
activity!!
}
}
enum class Status {
GRANTED, UN_GRANTED, TEMPORARY_DENIED, PERMANENT_DENIED
}
interface Listener {
fun onComplete(grantedPermissions: Set<String>, deniedPermissions: Set<String>)
fun onShowPermissionRationale(permissions: Set<String>): Boolean
fun onShowSettingRationale(permissions: Set<String>): Boolean
}
companion object {
const val REQUEST_CODE = 200
}
}
Run Code Online (Sandbox Code Playgroud)
使用在Activity像
class MainActivity : AppCompatActivity() {
private lateinit var smsAndStoragePermissionHandler: RequestPermissionHandler
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
smsAndStoragePermissionHandler = RequestPermissionHandler(this@MainActivity,
permissions = setOf(Manifest.permission.RECEIVE_SMS, Manifest.permission.READ_EXTERNAL_STORAGE),
listener = object : RequestPermissionHandler.Listener {
override fun onComplete(grantedPermissions: Set<String>, deniedPermissions: Set<String>) {
Toast.makeText(this@MainActivity, "complete", Toast.LENGTH_SHORT).show()
text_granted.text = "Granted: " + grantedPermissions.toString()
text_denied.text = "Denied: " + deniedPermissions.toString()
}
override fun onShowPermissionRationale(permissions: Set<String>): Boolean {
AlertDialog.Builder(this@MainActivity).setMessage("To able to Send Photo, we need SMS and" + " Storage permission")
.setPositiveButton("OK") { _, _ ->
smsAndStoragePermissionHandler.retryRequestDeniedPermission()
}
.setNegativeButton("Cancel") { dialog, _ ->
smsAndStoragePermissionHandler.cancel()
dialog.dismiss()
}
.show()
return true // don't want to show any rationale, just return false here
}
override fun onShowSettingRationale(permissions: Set<String>): Boolean {
AlertDialog.Builder(this@MainActivity).setMessage("Go Settings -> Permission. " + "Make SMS on and Storage on")
.setPositiveButton("Settings") { _, _ ->
smsAndStoragePermissionHandler.requestPermissionInSetting()
}
.setNegativeButton("Cancel") { dialog, _ ->
smsAndStoragePermissionHandler.cancel()
dialog.cancel()
}
.show()
return true
}
})
button_request.setOnClickListener { handleRequestPermission() }
}
private fun handleRequestPermission() {
smsAndStoragePermissionHandler.requestPermission()
}
override fun onRequestPermissionsResult(requestCode: Int, permissions: Array<String>,
grantResults: IntArray) {
super.onRequestPermissionsResult(requestCode, permissions, grantResults)
smsAndStoragePermissionHandler.onRequestPermissionsResult(requestCode, permissions,
grantResults)
}
override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
super.onActivityResult(requestCode, resultCode, data)
smsAndStoragePermissionHandler.onActivityResult(requestCode)
}
}
Run Code Online (Sandbox Code Playgroud)
Ano*_*p M 10
Android-M ie,API 23引入了运行时权限,用于减少Android设备中的安全漏洞,用户现在可以在运行时直接管理应用程序权限.如果用户拒绝您的应用程序的特定权限,则必须通过询问权限对话框来获取它您在查询中提到的.
因此,请检查操作之前,即检查您是否有权访问资源链接,如果您的应用程序没有该特定权限,您可以请求权限链接并处理权限请求响应,如下所示.
@Override
public void onRequestPermissionsResult(int requestCode,
String permissions[], int[] grantResults) {
switch (requestCode) {
case MY_PERMISSIONS_REQUEST_READ_CONTACTS: {
// If request is cancelled, the result arrays are empty.
if (grantResults.length > 0
&& grantResults[0] == PackageManager.PERMISSION_GRANTED) {
// permission was granted, yay! Do the
// contacts-related task you need to do.
} else {
// permission denied, boo! Disable the
// functionality that depends on this permission.
}
return;
}
// other 'case' lines to check for other
// permissions this app might request
}
}
Run Code Online (Sandbox Code Playgroud)
最后,如果您计划使用新版本以避免强制关闭,那么通过行为更改是一个很好的做法:)
您可以在此处查看官方示例应用程序.
小智 6
从Android Marshmallow(API 23)及以上版本默认禁用所有危险权限(根据官方doc 官方文档).在应用程序第一次打开时安装后,您必须在运行时授予权限.
我实现了以下方式:
public class MarshMallowPermission {
public static final int EXTERNAL_STORAGE_PERMISSION_REQUEST_CODE_BY_GALLERY = 0;
public static final int EXTERNAL_STORAGE_PERMISSION_REQUEST_CODE_BY_CAMERA = 1;
public static final int EXTERNAL_STORAGE_PERMISSION_REQUEST_CODE_BY_LOAD_PROFILE = 2;
public static final int CAMERA_PERMISSION_REQUEST_CODE = 3;
public static final int LOCATION_PERMISSION_REQUEST_CODE = 4;
Activity activity;
Context mContext;
public MarshMallowPermission(Activity activity) {
this.activity = activity;
this.mContext = activity;
}
public boolean checkPermissionForExternalStorage(){
int result = ContextCompat.checkSelfPermission(activity, Manifest.permission.WRITE_EXTERNAL_STORAGE);
if (result == PackageManager.PERMISSION_GRANTED){
return true;
} else {
return false;
}
}
public boolean checkPermissionForCamera(){
int result = ContextCompat.checkSelfPermission(activity, Manifest.permission.CAMERA);
if (result == PackageManager.PERMISSION_GRANTED){
return true;
} else {
return false;
}
}
public boolean checkLocationPermission(){
int result = ActivityCompat.checkSelfPermission(activity, Manifest.permission.ACCESS_FINE_LOCATION);
if (result == PackageManager.PERMISSION_GRANTED){
return true;
} else {
return false;
}
}
public void requestPermissionForExternalStorage(int requestCode){
if (ActivityCompat.shouldShowRequestPermissionRationale(activity, Manifest.permission.WRITE_EXTERNAL_STORAGE)){
Toast.makeText(mContext.getApplicationContext(), "External Storage permission needed. Please allow in App Settings for additional functionality.", Toast.LENGTH_LONG).show();
} else {
ActivityCompat.requestPermissions(activity,new String[]{Manifest.permission.WRITE_EXTERNAL_STORAGE},requestCode);
}
}
public void requestPermissionForCamera(){
if (ActivityCompat.shouldShowRequestPermissionRationale(activity, Manifest.permission.CAMERA)){
Toast.makeText(mContext.getApplicationContext(), "Camera permission needed. Please allow in App Settings for additional functionality.", Toast.LENGTH_LONG).show();
} else {
ActivityCompat.requestPermissions(activity,new String[]{Manifest.permission.CAMERA},CAMERA_PERMISSION_REQUEST_CODE);
}
}
public void requestPermissionForLocation(){
if (ActivityCompat.shouldShowRequestPermissionRationale(activity, Manifest.permission.ACCESS_FINE_LOCATION) && ActivityCompat.shouldShowRequestPermissionRationale(activity, Manifest.permission.ACCESS_COARSE_LOCATION)){
Toast.makeText(mContext.getApplicationContext(), "Location permission needed. Please allow in App Settings for additional functionality.", Toast.LENGTH_LONG).show();
} else {
ActivityCompat.requestPermissions(activity, new String[]{Manifest.permission.ACCESS_FINE_LOCATION,Manifest.permission.ACCESS_COARSE_LOCATION}, LOCATION_PERMISSION_REQUEST_CODE);
}
}
}
Run Code Online (Sandbox Code Playgroud)
在您的活动课程中:
public class MainActivity extends AppCompatActivity{
private MarshMallowPermission marshMallowPermission;
@Override
protected void onCreate(Bundle savedInstanceState) {
Log.d("NavHome", "Oncreate_nav");
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
marshMallowPermission = new MarshMallowPermission(MainActivity.this);
if (!marshMallowPermission.checkPermissionForExternalStorage()) {
marshMallowPermission.requestPermissionForExternalStorage(MarshMallowPermission.EXTERNAL_STORAGE_PERMISSION_REQUEST_CODE_BY_LOAD_PROFILE);
}
}
@Override
public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {
super.onRequestPermissionsResult(requestCode, permissions, grantResults);
switch (requestCode) {
case MarshMallowPermission.EXTERNAL_STORAGE_PERMISSION_REQUEST_CODE_BY_LOAD_PROFILE:
if (grantResults.length > 0
&& grantResults[0] == PackageManager.PERMISSION_GRANTED) {
//permission granted successfully
} else {
//permission denied
}
break;
}
}
}
Run Code Online (Sandbox Code Playgroud)
将权限添加到 AndroidManifest.xml
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
<application ...>
....
</application>
Run Code Online (Sandbox Code Playgroud)
检查 Android 版本是否需要运行时权限。
if (Build.VERSION.SDK_INT > Build.VERSION_CODES.LOLLIPOP_MR1) {
askForPermission(Manifest.permission.WRITE_EXTERNAL_STORAGE, 1);
}
Run Code Online (Sandbox Code Playgroud)
如果未授予,请要求用户授予权限。
private void askForPermission(String permission, int requestCode) {
if (ContextCompat.checkSelfPermission(c, permission)
!= PackageManager.PERMISSION_GRANTED) {
if (ActivityCompat.shouldShowRequestPermissionRationale(MainActivity.this, permission)) {
Toast.makeText(c, "Please grant the requested permission to get your task done!", Toast.LENGTH_LONG).show();
ActivityCompat.requestPermissions(MainActivity.this, new String[]{permission}, requestCode);
} else {
ActivityCompat.requestPermissions(MainActivity.this, new String[]{permission}, requestCode);
}
}
}
Run Code Online (Sandbox Code Playgroud)
如果许可被授予与否,做一些事情。
@Override
public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {
switch (requestCode) {
case 1:
if (grantResults[0] == PackageManager.PERMISSION_GRANTED) {
//permission with request code 1 granted
Toast.makeText(this, "Permission Granted" , Toast.LENGTH_LONG).show();
} else {
//permission with request code 1 was not granted
Toast.makeText(this, "Permission was not Granted" , Toast.LENGTH_LONG).show();
}
break;
default:
super.onRequestPermissionsResult(requestCode, permissions, grantResults);
}
}
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
236580 次 |
| 最近记录: |