Compose笔记(八)--权限

        这一节主要了解一下Compose中权限的申请,其中主要用到accompanist-permissions这个权限库,它是一个简化的Android Compose 中权限管理的库,如下使用:

栗子:

依赖添加

dependencies {
    implementation("com.google.accompanist:accompanist-permissions:0.31.2-alpha")
}

单个权限

@OptIn(ExperimentalPermissionsApi::class)
@Composable
fun PermissionExample() {
    val permissionState = rememberPermissionState(
        permission = Manifest.permission.CAMERA
    )

    Scaffold(topBar = {
        TopAppBar(title = { Text("Permission Apply Test") })
    }) {
        Column(
            Modifier.fillMaxSize(),
            horizontalAlignment = Alignment.CenterHorizontally,
            verticalArrangement = Arrangement.Center
        ) {

            when (permissionState.status) {
                PermissionStatus.Granted -> {
                    Text("已经同意了相机权限")
                }
                is PermissionStatus.Denied -> {
                    Column {
                        val text = if (permissionState.status.shouldShowRationale) {
                            "相机权限已拒绝,点击按钮再次请求"
                        } else {
                            "相机权限已被禁止"
                        }
                        Text(text = text)
                        Button(onClick = {
                            permissionState.launchPermissionRequest()
                        }) {
                            Text("点击获取权限")
                        }
                    }
                }
            }
        }
    }
}

多个权限

清单文件:

<uses-permission android:name="android.permission.CAMERA" />
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />



import android.Manifest
import android.content.pm.PackageManager
import androidx.activity.compose.rememberLauncherForActivityResult
import androidx.activity.result.contract.ActivityResultContracts
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.material.Button
import androidx.compose.material.Scaffold
import androidx.compose.material.Text
import androidx.compose.material.TopAppBar
import androidx.compose.runtime.Composable
import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.setValue
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.platform.LocalContext
import androidx.core.app.ActivityCompat
import com.google.accompanist.permissions.ExperimentalPermissionsApi
import com.google.accompanist.permissions.PermissionStatus
import com.google.accompanist.permissions.rememberMultiplePermissionsState
import com.google.accompanist.permissions.rememberPermissionState
import com.google.accompanist.permissions.shouldShowRationale

@OptIn(ExperimentalPermissionsApi::class)
@Composable
fun MultiplePermissionsExample() {
    // 创建一个多权限状态对象,用于管理相机和存储权限
    val permissionsState = rememberMultiplePermissionsState(
        permissions = listOf(
            Manifest.permission.CAMERA,
            Manifest.permission.READ_EXTERNAL_STORAGE
        )
    )

    Column(
        modifier = Modifier.fillMaxSize(),
        verticalArrangement = Arrangement.Center,
        horizontalAlignment = Alignment.CenterHorizontally
    ) {
        val allPermissionsGranted = permissionsState.allPermissionsGranted
        val shouldShowRationale = permissionsState.shouldShowRationale

        if (allPermissionsGranted) {
            Text("所有权限已授予,可以使用相关功能。")
        } else {
            Column {
                if (shouldShowRationale) {
                    Text("为了正常使用应用功能,请授予以下权限:相机、存储。")
                }
                Button(onClick = { permissionsState.launchMultiplePermissionRequest() }) {
                    Text("请求权限")
                }
            }
        }
    }
}

注意:

1 依赖添加:确保在项目的 build.gradle(或 build.gradle.kts)文件中正确添加了 accompanist-permissions 库的依赖。同时,要注意使用与项目中其他 Compose 库版本兼容的 accompanist-permissions 版本,避免因版本不兼容导致编译错误或运行时异常。

2 注解使用:accompanist-permissions 库中的部分 API 被标记为 @ExperimentalPermissionsApi,这表示这些 API 还处于实验阶段,可能会在未来的版本中发生重大变化。在使用这些 API 时,需要在使用的函数或类上添加 @OptIn(ExperimentalPermissionsApi::class) 注解,以表明你已经了解并愿意承担使用实验性 API 的风险。

3 预先检查权限:在请求权限之前,应该先检查应用是否已经拥有该权限,避免不必要的权限请求对话框弹出,提升用户体验。可以使用 rememberPermissionState 或 rememberMultiplePermissionsState 返回的状态对象的相关属性进行检查。

原理

1. 基于 Android 系统的权限管理机制
Android 系统从 Android 6.0(API 级别 23)开始引入了运行时权限机制,应用需要在运行时请求某些危险权限。系统提供了一系列的 API 来处理权限请求,例如 ActivityCompat.requestPermissions 用于发起权限请求,ActivityCompat.checkSelfPermission 用于检查权限状态,ActivityCompat.shouldShowRequestPermissionRationale 用于判断是否需要向用户解释为什么需要该权限。

2 状态管理与响应式编程
Compose 是一种声明式的 UI 框架,它基于响应式编程模型,通过状态的变化来驱动 UI 的更新。accompanist-permissions 库利用了 Compose 的状态管理机制,将权限状态封装成可观察的状态对象,当权限状态发生变化时,自动触发 UI 的更新。

  2.1 rememberPermissionState 和 rememberMultiplePermissionsState这两个函数是 accompanist-permissions 库的核心,用于创建权限状态对象。
rememberPermissionState:用于管理单个权限的状态。它返回一个 PermissionState 对象,该对象包含了权限的当前状态信息,如 hasPermission(权限是否已授予)、shouldShowRationale(是否需要显示权限请求说明)等。这些状态信息会随着权限请求结果的变化而自动更新,从而触发 Compose UI 的重组。
rememberMultiplePermissionsState:用于管理多个权限的状态。它返回一个 MultiplePermissionsState 对象,该对象可以跟踪多个权限的授予情况,通过 allPermissionsGranted 判断所有权限是否都已授予,通过 shouldShowRationale 判断是否有任何权限需要显示请求说明。

3. 权限请求处理
accompanist-permissions 库封装了权限请求的逻辑,通过 launchPermissionRequest 和 launchMultiplePermissionRequest 方法来发起权限请求。
 3.1 内部实现
当调用 launchPermissionRequest 或 launchMultiplePermissionRequest 方法时,库会使用 Android 系统的 ActivityResultLauncher 来发起权限请求。ActivityResultLauncher 是 Android 系统提供的一种用于处理 Activity 结果的机制,它可以在请求权限后自动接收权限请求结果,并将结果传递给回调函数。

class PermissionStateImpl(
    private val permission: String,
    private val activity: ComponentActivity
) : PermissionState {
    private val _hasPermission = mutableStateOf(false)
    private val _shouldShowRationale = mutableStateOf(false)

    override val hasPermission: Boolean
        get() = _hasPermission.value

    override val shouldShowRationale: Boolean
        get() = _shouldShowRationale.value

    private val permissionLauncher = activity.registerForActivityResult(
        ActivityResultContracts.RequestPermission()
    ) { isGranted ->
        _hasPermission.value = isGranted
        _shouldShowRationale.value = activity.shouldShowRequestPermissionRationale(permission)
    }

    override fun launchPermissionRequest() {
        permissionLauncher.launch(permission)
    }
}

4. 状态更新与 UI 重组
        当权限请求结果返回时,accompanist-permissions 库会更新权限状态对象的状态信息。由于这些状态信息是使用 Compose 的 MutableState 封装的,当状态发生变化时,Compose 会自动检测到这些变化,并触发相关 UI 组件的重组,从而更新 UI 显示。例如,当用户授予相机权限后,cameraPermissionState.hasPermission 的值会从 false 变为 true,Compose 会重新执行 if (cameraPermissionState.hasPermission) 语句块,更新 UI 显示为 “相机权限已授予”。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/983953.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

从0到1入门RabbitMQ

一、同步调用 优势&#xff1a;时效性强&#xff0c;等待到结果后才返回 缺点&#xff1a; 拓展性差性能下降级联失败问题 二、异步调用 优势&#xff1a; 耦合度低&#xff0c;拓展性强异步调用&#xff0c;无需等待&#xff0c;性能好故障隔离&#xff0c;下游服务故障不影响…

CST直角反射器 --- 距离多普勒(RD图), 毫米波汽车雷达ADAS

之前几期介绍了雷达是如何从频域换去时域&#xff0c;然后时域计算距离。 这期我们加上一个维度&#xff0c;既看距离&#xff0c;又看速度。速度的计算当然就是多普勒原理&#xff0c;所以距离速度的二维图又叫range-doppler图。 启用雷达ADAS Range-Doppler模板&#xff1a…

手写一个Tomcat

Tomcat 是一个广泛使用的开源 Java Servlet 容器&#xff0c;用于运行 Java Web 应用程序。虽然 Tomcat 本身功能强大且复杂&#xff0c;但通过手写一个简易版的 Tomcat&#xff0c;我们可以更好地理解其核心工作原理。本文将带你一步步实现一个简易版的 Tomcat&#xff0c;并深…

【从零开始学习计算机科学】计算机组成原理(六)异常事件处理

【从零开始学习计算机科学】计算机组成原理&#xff08;六&#xff09;异常事件处理 异常事件处理异常处理的数据通路异常事件入口地址 异常事件处理 异常和中断事件改变处理机正常指令的执行顺序。异常指令执行过程中&#xff0c;由于操作非法和指令非法引起的事件。陷阱指陷…

3.3.2 Proteus第一个仿真图

文章目录 文章介绍0 效果图1 新建“点灯”项目2 添加元器件3 元器件布局接线4 补充 文章介绍 本文介绍&#xff1a;使用Proteus仿真软件画第一个仿真图 0 效果图 1 新建“点灯”项目 修改项目名称和路径&#xff0c;之后一直点“下一步”直到完成 2 添加元器件 点击元…

高效运行 QwQ-32B + 错误修复

文章目录 QwQ-32B 错误修复⚙️ 官方推荐设置&#x1f44d; 推荐的 llama.cpp 设置&#x1f4d6; 教程&#xff1a;运行和修复的 QwQ-32B1、对于 llama.cpp 及使用 llama.cpp 的引擎&#xff1a;2、下载模型 测试3、测试/评估4、尝试不使用我们的修复方案&#xff1a; &#x…

R 语言科研绘图 --- 直方图-汇总

在发表科研论文的过程中&#xff0c;科研绘图是必不可少的&#xff0c;一张好看的图形会是文章很大的加分项。 为了便于使用&#xff0c;本系列文章介绍的所有绘图都已收录到了 sciRplot 项目中&#xff0c;获取方式&#xff1a; R 语言科研绘图模板 --- sciRplothttps://mp.…

1.5.1 掌握Scala内建控制结构 - 条件表达式

本文介绍了 Scala 中条件表达式的使用及其在实际任务中的应用。条件表达式的语法为 if (条件) 值1 else 值2&#xff0c;其结果类型取决于值1和值2的类型。如果类型相同&#xff0c;结果类型与它们相同&#xff1b;如果不同&#xff0c;则结果类型为 Any。通过两个任务展示了条…

Linux rootfs:如何开机就自动添加某个用户?

前言 项目开发需求&#xff0c;需要开机后就自动创建某个用户密码 厂家提供的sdk&#xff0c;只有adduser命令&#xff0c; 该命令添加用户时&#xff0c;会有终端交互&#xff0c; 需要手动输入2次密码&#xff0c; 所以无法通过简单脚本方式创建。 要实现自动填充密码&…

计算机三级网络技术知识点汇总【7】

第七章 路由器配置及使用 1. 路由器的基础知识 1.1 路由器的基本概念 路由器是工作在网络层的设备&#xff0c;负责将数据分组从源端主机经最佳路径传送到目的端主机&#xff0c;实现在网络层的互联。路由器工作在 TCP/IP 网络模型的网络层&#xff0c;对应于 OSI 网络参考模…

Compounding Geometric Operations for Knowledge Graph Completion(论文笔记)

CCF等级&#xff1a;A 发布时间&#xff1a;2023年7月 25年3月10日交 一、简介 使用知识图谱嵌入模型&#xff0c;将三元组&#xff08;h,r,t&#xff09;中关系 r 转化为平移、旋转、缩放矩阵对头节点以及尾节点进行运算&#xff0c;判定三元组的真实性。 二、原理 1.整…

mac系统安装

目录 准备工作 一、安装虚拟机 二、解锁系统 三、安装系统 四、部署系统 五、安装VMware Tools(选做) 为什么要安装VMware Tools,这是啥玩意? 六、配置共享文件夹(选做) 为什么要共享文件夹? 注意事项: 七、安装完成 准备工作 一、安装说明: 本教程分为7个部…

DNASimCLR:一种基于对比学习的基因序列数据分类的深度学习方法

摘要 DNASimCLR利用卷积神经网络和基于对比学习的SimCLR框架&#xff0c;从不同的微生物基因序列中提取复杂的特征。在包含宏基因组和病毒基因序列的两个经典的大规模未标记数据集上进行了预训练。后续的分类任务通过使用先前获得的模型对预训练的模型进行微调来完成。我们的实…

Ae 效果详解:VR 旋转球面

Ae菜单&#xff1a;效果/沉浸式视频/VR 旋转球面 Immersive Video/VR Rotate Sphere VR 旋转球面 VR Rotate Sphere效果用于对 VR 视频进行三轴旋转&#xff0c;以调整视频的视角方向。可用于校正拍摄时的角度偏差&#xff0c;或者根据创意需求模拟摄像机旋转。 本效果适用于所…

南开提出1Prompt1Story,无需训练,可通过单个连接提示实现一致的文本到图像生成。

&#xff08;1Prompt1Story&#xff09;是一种无训练的文本到图像生成方法&#xff0c;通过整合多个提示为一个长句子&#xff0c;并结合奇异值重加权&#xff08;SVR&#xff09;和身份保持交叉注意力&#xff08;IPCA&#xff09;技术&#xff0c;解决了生成图像中身份不一致…

Python----数据可视化(Seaborn二:绘图一)

常见方法 barplot方法 单独绘制条形图 catplot方法 可以条形图、散点图、盒图、小提亲图、等 countplot方法 统计数量 一、柱状图 seaborn.barplot(dataNone, xNone, yNone, hueNone, colorNone, paletteNone) 函数描述data用于绘图的数据集。x用于绘制长格式数据的输入。…

只音 1.2.0 |纯净无广告,畅听全网音乐,支持无损下载和批量下载

只音是一款全网音乐一网打尽的听歌利器&#xff0c;无需登录即可搜索抖音、网易云、QQ音乐等平台资源&#xff0c;无损音质直连播放。内置智能推荐算法&#xff0c;每日更新热门榜单与个性化歌单&#xff0c;轻松发现小众优质音乐。支持批量下载功能&#xff0c;一次性打包30首…

Python从入门到精通1:FastAPI

引言 在现代 Web 开发中&#xff0c;API 是前后端分离架构的核心。FastAPI 凭借其高性能、简洁的语法和自动文档生成功能&#xff0c;成为 Python 开发者的首选框架。本文将从零开始&#xff0c;详细讲解 FastAPI 的核心概念、安装配置、路由设计、请求处理以及实际应用案例&a…

Service与Ingress:如何将你的应用暴露给世界

引言&#xff1a;从“内部通讯”到“对外开放” 想象Kubernetes集群是一座繁忙的办公楼&#xff0c;每个Pod&#xff08;容器&#xff09;是楼内的员工。 Service 就像前台的接待员&#xff0c;负责将外部电话&#xff08;请求&#xff09;转接到正确的员工&#xff08;Pod&am…

【Linux学习篇】--开发工具第一期

目录 1. Linux编辑器的使用--vim使用 1.1 vim的基本概念 1.2 vim基本操作 1.3 vim正常模式&#xff08;指令模式&#xff09;命令集 1.4 vim末行模式命令集 1.5 vim配置 2. Linux编译器-gcc/g使用 2.1 背景知识 2.2 gcc如何完成 2.3 gcc选择项 1. Linux编…