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

Android -- DragDrop


Android3.0提供了drag/drop框架,利用此框架可以实现使用拖放手势将一个view拖放到当前布局中的另外一个view中。

实现拖放的步骤

首先,我们先了解一下拖放过程,从官方文档可以知道,整个拖放过程共分为4个步骤,具体如下:

1、  Started:启动拖放,主要是调用被拖放View的startDrag方法。此方法原型为:

public final boolean startDrag(ClipData data, View.DragShadowBuilder shadowBuilder, Object myLocalState,  int flags)

启动后,系统生成拖放阴影并发送action为ACTION_DRAG_STARTED的拖放事件到当前布局中已经设置了拖放监听的View。

2、  Continuing:保持拖动状态。在此过程中系统可能会发送一个或多个拖动事件给设置了拖放监听器的View,比如ACTION_DRAG_ENTERED、ACTION_DRAG_LOCATION等。

3、  Dropped:用户在目标区域内释放拖动阴影,系统会向设置了拖放监听器的View发送action为ACTION_DROP的事件。

4、  Ended:用户释放了拖动阴影,系统会向设置了拖放监听器的View发送action为ACTION_DRAG_ENDED事件,完成拖放。

拖放过程中关键的接口和类

其次,我们要了解清楚拖放过程中的几个关键的接口和类,主要有OnDragListener、DragEvent、DragShadowBuilder、ClipData、ClipDescription等。

1、OnDragListener:接口,拖放事件监听器。当发生Drag时,回调此接口中的方法。接口中只含有一个方法onDrag,方法原型为:

boolean onDrag(View v, DragEvent event)
//参数v:设置了监听器的View
//参数event:拖放事件的参数,封装了拖放相关的数据
//返回值:true-事件已处理;false事件未处理。

2、DragEvent:拖放事件对象,根据action的不同,包含不同的事件数据。

3、DragShadowBuilder:拖放阴影构造者对象,用于构造拖放阴影。

4、ClipData、ClipDescription:用于拖放的移动数据。

code

复制代码
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/topContainer"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical" >

    <ImageView
        android:id="@+id/img"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:contentDescription="@null"
        android:src="@drawable/ic_launcher" />

    <LinearLayout
        android:id="@+id/container"
        android:layout_width="match_parent"
        android:layout_height="100dp"
        android:layout_alignParentBottom="true"
        android:orientation="vertical"
        android:background="#cccccc" >
        <TextView
            android:id="@+id/title"
            android:layout_width="fill_parent"
            android:layout_height="wrap_content"
            android:textColor="#ff0000"
            android:textSize="18sp" />
    </LinearLayout>

</RelativeLayout>
复制代码

为ImageView绑定长点击事件

复制代码
imageView.setOnLongClickListener(new OnLongClickListener() {
            @Override
            public boolean onLongClick(View v) {
                //创建移动数据
                ClipData.Item item = new ClipData.Item((String) v.getTag());
                ClipData data = new ClipData(IMAGEVIEW_TAG,
                        new String[] { ClipDescription.MIMETYPE_TEXT_PLAIN },
                        item);
                //调用startDrag方法,第二个参数为创建拖放阴影
                v.startDrag(data, new View.DragShadowBuilder(v), null, 0);
                return true;
            }
        });
复制代码

为目标View绑定拖拽监听:

复制代码
container.setOnDragListener(new OnDragListener() {
            @Override
            public boolean onDrag(View v, DragEvent event) {
                final int action = event.getAction();
                switch (action) {
                case DragEvent.ACTION_DRAG_STARTED:
                    //拖拽开始事件
                    if (event.getClipDescription().hasMimeType(
                            ClipDescription.MIMETYPE_TEXT_PLAIN)) {
                        return true;
                    }
                    return false;
                case DragEvent.ACTION_DRAG_ENTERED:
                    //被拖放View进入目标View
                    container.setBackgroundColor(Color.YELLOW);
                    return true;
                case DragEvent.ACTION_DRAG_LOCATION:
                    return true;
                case DragEvent.ACTION_DRAG_EXITED:
                    //被拖放View离开目标View
                    container.setBackgroundColor(Color.BLUE);
                    title.setText("");
                    return true;
                case DragEvent.ACTION_DROP:
                    //释放拖放阴影,并获取移动数据
                    ClipData.Item item = event.getClipData().getItemAt(0);
                    String dragData = item.getText().toString();
                    title.setText(dragData+event.getY()+":"+event.getX());
                    return true;
                case DragEvent.ACTION_DRAG_ENDED:
                    //拖放事件完成
                    return true;
                default:
                    break;
                }
                return false;
            }
        });
复制代码

imageView的位置

复制代码
topContainer.setOnDragListener(new OnDragListener() {
            @Override
            public boolean onDrag(View v, DragEvent event) {
                final int action = event.getAction();
                switch (action) {
                case DragEvent.ACTION_DRAG_STARTED:
                    return true;
                case DragEvent.ACTION_DRAG_ENTERED:
                    return true;
                case DragEvent.ACTION_DRAG_LOCATION:
                    return true;
                case DragEvent.ACTION_DRAG_EXITED:
                    return true;
                case DragEvent.ACTION_DROP:
                    imageView.setX(event.getX()-imageView.getWidth()/2);
                    imageView.setY(event.getY()-imageView.getHeight()/2);
                    return true;
                case DragEvent.ACTION_DRAG_ENDED:
                    return true;
                default:
                    break;
                }
                return false;
            }
        });
复制代码

效果

123

我是天王盖地虎的分割线

 




本文转自我爱物联网博客园博客,原文链接:http://www.cnblogs.com/yydcdut/p/4473992.html,如需转载请自行联系原作者

相关文章:

  • 一个完整Java Web项目背后的密码
  • PHP字符串操作(string替换、删除、截取、复制、连接、比较、查找、包含、大小写转换、切割成数组等)...
  • vue element ui excel json2csv csv 导出
  • 这7个不可错过的数据可视化技术,让你的位置信息跃然纸上
  • JAVA运维-Tomcat支持APR模式
  • 路由器密码忘了怎么办 自己动手不求人
  • 源码编译安装 PHP 7.1.5 + nginx 1.12.0
  • 微信分享JS-SDK
  • 独家 | 环境大数据的应用案例及前景
  • P4165 [SCOI2007]组队
  • 跨域问题
  • laraval+node.js实现websocket
  • PowerShell 脚本执行策略
  • MSDN SmartCast更改下载步骤
  • QT之二维绘图:场景,图元,视图
  • [译] 怎样写一个基础的编译器
  • 【node学习】协程
  • 【技术性】Search知识
  • 【腾讯Bugly干货分享】从0到1打造直播 App
  • Centos6.8 使用rpm安装mysql5.7
  • css选择器
  • JavaScript标准库系列——Math对象和Date对象(二)
  • Java教程_软件开发基础
  • Less 日常用法
  • Node 版本管理
  • PHP CLI应用的调试原理
  • PHP面试之三:MySQL数据库
  • React-Native - 收藏集 - 掘金
  • 从零开始的webpack生活-0x009:FilesLoader装载文件
  • 关于 Linux 进程的 UID、EUID、GID 和 EGID
  • 微信开源mars源码分析1—上层samples分析
  • Mac 上flink的安装与启动
  • 阿里云IoT边缘计算助力企业零改造实现远程运维 ...
  • ​RecSys 2022 | 面向人岗匹配的双向选择偏好建模
  • ​人工智能之父图灵诞辰纪念日,一起来看最受读者欢迎的AI技术好书
  • #QT(一种朴素的计算器实现方法)
  • (5)STL算法之复制
  • (HAL)STM32F103C6T8——软件模拟I2C驱动0.96寸OLED屏幕
  • (JSP)EL——优化登录界面,获取对象,获取数据
  • (八)Flask之app.route装饰器函数的参数
  • (附源码)springboot家庭财务分析系统 毕业设计641323
  • (附源码)ssm户外用品商城 毕业设计 112346
  • (学习日记)2024.03.12:UCOSIII第十四节:时基列表
  • .“空心村”成因分析及解决对策122344
  • .bat批处理出现中文乱码的情况
  • .mat 文件的加载与创建 矩阵变图像? ∈ Matlab 使用笔记
  • .Net 6.0 处理跨域的方式
  • .NET DevOps 接入指南 | 1. GitLab 安装
  • .NET MAUI学习笔记——2.构建第一个程序_初级篇
  • .NET 使用配置文件
  • .Net通用分页类(存储过程分页版,可以选择页码的显示样式,且有中英选择)
  • @Async注解的坑,小心
  • @test注解_Spring 自定义注解你了解过吗?
  • [ vulhub漏洞复现篇 ] ThinkPHP 5.0.23-Rce
  • [2019/05/17]解决springboot测试List接口时JSON传参异常