当前位置: 首页 > news >正文

Compose笔记(二十三)--多点触控

         这一节主要了解一下Compose中多点触控,在Jetpack Compose 中,多点触控处理需要结合Modifier和手势API来实现,一般通过组合 pointerInput、TransformableState 和 TransformModifier 来创建支持缩放、旋转和平移的组件。

一、 API
1. PointerInput
含义:处理低级触摸事件的主要API,支持多点触控。
用法:通过pointerInput修饰符拦截和处理触摸事件。
2. TransformableState
含义:管理变换状态(缩放、旋转、平移)的状态容器。
用法:与transformable修饰符结合,监听手势并更新变换值。
3. TransformModifier
含义:应用变换效果(缩放、旋转、平移)的修饰符。
用法:通过graphicsLayer或transformable应用变换。
二、关键类与接口
1. PointerInputScope
提供处理触摸事件的作用域,包含:
detectDragGestures:处理单指拖拽。
detectTransformGestures:处理双指缩放 / 旋转。
detectTapGestures:处理点击事件。
2. TransformScope
在detectTransformGestures中提供:
panChange:平移变化量。
zoomChange:缩放变化量。
rotationChange:旋转变化量。
3. Transformation
包含三个变换参数:
scale:缩放因子。
rotation:旋转角度。
offset:平移偏移量。

栗子:

1. 单指拖拽

import androidx.compose.foundation.Image
import androidx.compose.foundation.background
import androidx.compose.foundation.gestures.detectDragGestures
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.foundation.layout.size
import androidx.compose.runtime.Composable
import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.remember
import androidx.compose.runtime.setValue
import androidx.compose.ui.Modifier
import androidx.compose.ui.geometry.Offset
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.graphics.graphicsLayer
import androidx.compose.ui.input.pointer.consumeAllChanges
import androidx.compose.ui.input.pointer.pointerInput
import androidx.compose.ui.res.painterResource
import androidx.compose.ui.unit.dp
import com.example.composenavigationdemo.R@Composable
fun TestImage() {var offset by remember { mutableStateOf(Offset.Zero) }Box(modifier = Modifier.size(200.dp).background(Color.LightGray).pointerInput(Unit) {detectDragGestures { change, dragAmount ->// 阻止事件冒泡change.consumeAllChanges()// 更新偏移量offset = offset + dragAmount}}.graphicsLayer {translationX = offset.xtranslationY = offset.y}) {Image(painter = painterResource(R.drawable.android),contentDescription = null,modifier = Modifier.fillMaxSize())}
}

2. 双指缩放与旋转

import androidx.compose.foundation.Image
import androidx.compose.foundation.background
import androidx.compose.foundation.gestures.detectTransformGestures
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.runtime.Composable
import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.remember
import androidx.compose.runtime.setValue
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.geometry.Offset
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.graphics.graphicsLayer
import androidx.compose.ui.input.pointer.pointerInput
import androidx.compose.ui.res.painterResource
import com.example.composenavigationdemo.R@Composable
fun TestImage() {var scale by remember { mutableStateOf(1f) }var rotation by remember { mutableStateOf(0f) }var offset by remember { mutableStateOf(Offset.Zero) }Box(modifier = Modifier.fillMaxSize().background(Color.LightGray).pointerInput(Unit) {detectTransformGestures { centroid, pan, zoom, rotationChange ->// 更新变换参数scale = (scale * zoom).coerceIn(0.5f, 5f)rotation += rotationChangeoffset = centroid}}) {Image(painter = painterResource(R.drawable.android),contentDescription = null,modifier = Modifier.align(Alignment.Center).graphicsLayer {scaleX = scalescaleY = scalerotationZ = rotationtranslationX = offset.x - size.width / 2translationY = offset.y - size.height / 2})}
}

3 组合多种手势

import androidx.compose.foundation.Image
import androidx.compose.foundation.background
import androidx.compose.foundation.gestures.detectDragGestures
import androidx.compose.foundation.gestures.detectTransformGestures
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.runtime.Composable
import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.remember
import androidx.compose.runtime.setValue
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.geometry.Offset
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.graphics.graphicsLayer
import androidx.compose.ui.input.pointer.pointerInput
import androidx.compose.ui.res.painterResource
import com.example.composenavigationdemo.R
import kotlinx.coroutines.coroutineScope
import kotlinx.coroutines.launch@Composable
fun TestImage() {var scale by remember { mutableStateOf(1f) }var rotation by remember { mutableStateOf(0f) }var offset by remember { mutableStateOf(Offset.Zero) }var isDragging by remember { mutableStateOf(false) }Box(modifier = Modifier.fillMaxSize().background(Color.LightGray).pointerInput(Unit) {coroutineScope {launch {detectDragGestures(onDragStart = { isDragging = true },onDragEnd = { isDragging = false }) { change, dragAmount ->offset += dragAmount}}launch {detectTransformGestures(panZoomLock = true) { _, pan, zoom, rotationChange ->scale *= zoomrotation += rotationChangeoffset += pan}}}}.graphicsLayer {scaleX = scalescaleY = scalerotationZ = rotationtranslationX = offset.xtranslationY = offset.y}) {Image(painter = painterResource(R.drawable.android),contentDescription = null,modifier = Modifier.align(Alignment.Center))}
}

注意:
1 事件消费:通过change.consumeAllChanges()阻止事件冒泡。
2 坐标系转换:注意centroid(双指中心点)和offset的坐标系差异。
3 状态管理:使用remember保存变换状态,确保配置变更后状态恢复。

http://www.xdnf.cn/news/498403.html

相关文章:

  • 1688 数据接口调用秘籍:高效获取商品实时信息的开发指南
  • Redis技术深度解析
  • Elasticsearch 查询与过滤(Query vs. Filter)面试题
  • Vue3(一)
  • 机器学习 KNN算法
  • 当硅基存在成为人性延伸的注脚:论情感科技重构社会联结的可能性
  • 震荡指标工具
  • 如何在 Windows 10 或 11 上通过命令行安装 Node.js 和 NPM
  • Redis配置与优化:提升NoSQL数据库性能的关键策略
  • MinIO深度解析:从入门到实战——对象存储系统全指南
  • 智慧水务关键一环:Profinet转Modbus TCP网关驱动供水系统高效互联
  • 蓝牙耳机什么牌子好?倍思值得冲不?
  • 软件设计师考试《综合知识》创建型设计模式考点分析
  • NY309NY318美光科技颗粒NY319NY320
  • SVN 版本控制入门指南
  • 项目QT+ffmpeg+rtsp(二)——海康威视相机测试
  • 【学习心得】英伟达的诸多显卡性能对比
  • Scrapy进阶实践指南:从脚本运行到分布式爬取
  • 基于 Python 的界面程序复现:标准干涉槽型设计计算及仿真
  • Linux面试题集合(3)
  • 二叉树进阶
  • c++重要知识点汇总(不定期更新)
  • flutter flutter run 运行项目卡在Running Gradle task ‘assembleDebug‘...
  • Linux基础开发工具二(gcc/g++,自动化构建makefile)
  • OpenCV级联分类器
  • gRPC开发指南:Visual Studio 2022 + Vcpkg + Windows全流程配置
  • ABP vNext 多租户开发实战指南
  • Uniapp开发鸿蒙应用时如何运行和调试项目
  • 中级统计师-统计学基础知识-第二章数据描述
  • 产品经理入门(2)产品体验报告