安卓多个listView拖动数据交换位置和拖动

注意这里只是给出大概思路,具体可以参考修改自己想要的


public class MainActivity extends AppCompatActivity {

    private ListView listView1;
    private ListView listView2;
    private ArrayAdapter<String> adapter1;
    private ArrayAdapter<String> adapter2;
    private int dragIndex = -1;
    private boolean isDragged1 = false;
    private boolean isDragged2 = false;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        listView1 = findViewById(R.id.listView1);
        listView2 = findViewById(R.id.listView2);

        adapter1 = new ArrayAdapter<>(this, android.R.layout.simple_list_item_1);
        adapter2 = new ArrayAdapter<>(this, android.R.layout.simple_list_item_1);

        listView1.setAdapter(adapter1);
        listView2.setAdapter(adapter2);

        adapter1.add("Item 1");
        adapter1.add("Item 2");
        adapter1.add("Item 3");

        adapter2.add("Item A");
        adapter2.add("Item B");
        adapter2.add("Item C");


        listView1.setOnItemLongClickListener((parent, view, position, id) -> {
            isDragged1 = true; // 标记列表1正在拖动
            dragIndex = position;
            ClipData data = ClipData.newPlainText("", "");
            View.DragShadowBuilder shadowBuilder = new View.DragShadowBuilder(view);
            view.startDrag(data, shadowBuilder, view, 0);
            return true;
        });

        listView2.setOnItemLongClickListener((parent, view, position, id) -> {
            isDragged2 = true; // 标记列表2正在拖动
            dragIndex = position;
            ClipData data = ClipData.newPlainText("", "");
            View.DragShadowBuilder shadowBuilder = new View.DragShadowBuilder(view);
            view.startDrag(data, shadowBuilder, view, 0);
            return true;
        });

        listView1.setOnDragListener(new MyDragListener());
        listView2.setOnDragListener(new MyDragListener());
    }




//多个 list拖动
    //    class MyDragListener implements View.OnDragListener {
//        @Override
//        public boolean onDrag(View v, DragEvent event) {
//            int action = event.getAction();
//            switch (action) {
//                case DragEvent.ACTION_DROP: // 当拖拽动作完成时
//                    if (v == listView2 && isDragged1) { // 如果目标是 listView2 且之前有拖拽操作
//                        String item1 = adapter1.getItem(dragIndex); // 获取拖拽的数据项
//                        adapter1.remove(item1); // 从原列表移除
//                        adapter2.add(item1); // 添加到新列表
//                        adapter1.notifyDataSetChanged(); // 刷新原列表
//                        adapter2.notifyDataSetChanged(); // 刷新新列表
//                    } else if (v == listView1 && isDragged2) { // 如果目标是 listView1 且之前有拖拽操作
//                        String item2 = adapter2.getItem(dragIndex); // 获取拖拽的数据项
//                        adapter2.remove(item2); // 从原列表移除
//                        adapter1.add(item2); // 添加到新列表
//                        adapter1.notifyDataSetChanged(); // 刷新原列表
//                        adapter2.notifyDataSetChanged(); // 刷新新列表
//                    }
//                    isDragged1 = false; // 拖动结束,重置标记
//                    isDragged2 = false;
//                    dragIndex = -1;
//                    break;
//            }
//            return true;
//        }
//    }


    /**
     * 拖动交换位置
     */
    class MyDragListener implements View.OnDragListener {
        @Override
        public boolean onDrag(View v, DragEvent event) {
            int action = event.getAction();
            switch (action) {
                case DragEvent.ACTION_DROP: // 当拖拽动作结束时
                    if (v == listView2 && isDragged1) {
                        String item1 = adapter1.getItem(dragIndex); // 获取拖拽源列表项数据
                        int targetPosition = getItemPositionFromPoint(event.getX(), event.getY(), listView2); // 获取目标位置
                        String item2 = adapter2.getItem(targetPosition); // 获取目标位置处的列表项数据
                        adapter1.remove(item1); // 从源列表中移除数据
                        adapter2.remove(item2); // 从目标列表中移除数据
                        adapter1.insert(item2, dragIndex); // 在源列表中插入数据
                        adapter2.insert(item1, targetPosition); // 在目标列表中插入数据
                        adapter1.notifyDataSetChanged(); // 更新源列表
                        adapter2.notifyDataSetChanged(); // 更新目标列表
                    } else if (v == listView1 && isDragged2) {
                        String item2 = adapter2.getItem(dragIndex); // 获取拖拽源列表项数据
                        int targetPosition = getItemPositionFromPoint(event.getX(), event.getY(), listView1); // 获取目标位置
                        String item1 = adapter1.getItem(targetPosition); // 获取目标位置处的列表项数据
                        adapter2.remove(item2); // 从源列表中移除数据
                        adapter1.remove(item1); // 从目标列表中移除数据
                        adapter2.insert(item1, dragIndex); // 在源列表中插入数据
                        adapter1.insert(item2, targetPosition); // 在目标列表中插入数据
                        adapter2.notifyDataSetChanged(); // 更新源列表
                        adapter1.notifyDataSetChanged(); // 更新目标列表
                    }
                    isDragged1 = false; // 拖动结束,重置标记
                    isDragged2 = false;
                    dragIndex = -1;
                    break;
            }
            return true;
        }

        // 根据坐标点获取列表项位置
        private int getItemPositionFromPoint(float x, float y, ListView listView) {
            int position = listView.pointToPosition((int) x, (int) y); // 根据坐标点获取位置
            int firstVisiblePosition = listView.getFirstVisiblePosition(); // 第一个可见项位置
            int lastVisiblePosition = listView.getLastVisiblePosition(); // 最后一个可见项位置
            if (position >= firstVisiblePosition && position <= lastVisiblePosition) {
                View itemView = listView.getChildAt(position - firstVisiblePosition); // 获取对应位置的视图
                if (itemView != null) {
                    int itemTop = itemView.getTop();
                    int itemBottom = itemView.getBottom();
                    int itemHeight = itemView.getHeight();
                    if (y >= itemTop + itemHeight / 2) { // 判断是否在列表项中部
                        return position;
                    }
                }
            }
            return position - 1; // 返回最终位置
        }
    }
}

布局

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="horizontal">

    <ListView
        android:id="@+id/listView1"
        android:layout_width="0dp"
        android:layout_height="match_parent"
        android:layout_weight="1" />

    <ListView
        android:id="@+id/listView2"
        android:layout_width="0dp"
        android:layout_height="match_parent"
        android:layout_weight="1" />

</LinearLayout>

效果图

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

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

相关文章

智慧路灯杆AI监测应用,让高速出行更安全

高速公路是现代交通出行的重要组成&#xff0c;高速公路上的交通安全也一直是人们关注的焦点。针对更好监测和管理高速公路上的交通状况&#xff0c;可以基于智慧路灯杆打造AI交通监测应用&#xff0c;通过智能感知高速路段的路况、车况、环境状况&#xff0c;实现实时风险感知…

解决pandas使用sqlalchemy保存到Mysql数据库时,bool布尔类型数据转为tinyint数据的读取

pandas在使用to_sql()保存数据到数据表中&#xff0c;Mysql会将bool类型的数据转为tinyint类型&#xff0c;比如&#xff1a; 此时数据表字段的类型为&#xff1a; 读取的时候&#xff0c;如果直接使用read_sql会原封不动的读取成1或0的数据&#xff0c;因此我们存储的时候…

Ubuntu 14.04:安装PaddlePaddle(Conda安装)

目录 一、PaddlePaddle 概要 二、PaddlePaddle安装要求 三、PaddlePaddle安装 3.1 安装 Anaconda3 3.2 创建Anaconda虚拟环境&#xff08;python 3.8&#xff09; 3.3 进入Anaconda虚拟环境 3.4 检测 Anaconda 虚拟环境配置是否符合PaddlePaddle安装要求 3.4.1 确认 py…

6.S081的Lab学习——Lab1: Xv6 and Unix utilities

文章目录 前言一、启动xv6(难度&#xff1a;Easy)解析&#xff1a; 二、sleep(难度&#xff1a;Easy)解析&#xff1a; 三、pingpong&#xff08;难度&#xff1a;Easy&#xff09;解析&#xff1a; 四、Primes(素数&#xff0c;难度&#xff1a;Moderate/Hard)解析&#xff1a…

C++初阶:类与对象(尾篇)

目录 1. 构造函数与初始化列表1.1 对象的创建与构造函数的初始化1.2 初始化列表及构造函数存在的意义1.3 explicit关键字与构造函数的类型转换 2. static成员变量与static成员函数2.1 static成员变量2.2 static成员函数 3. 日期类流插入操作符的重载与友元3.1 友元3.2 友元函数…

Ubuntu20.04配置静态ip

文章目录 前言配置静态ip 前言 在 Linux 创建时默认是动态 ip&#xff0c;我们需要将这台 Linux 作为服务器&#xff0c;所以需要将动态分配的 ip 设置为静态的&#xff0c;防止 ip 变换。 可使用 ip addr 查看当前的 网卡 和 ip 信息&#xff1a; 从上图可看到动态分配的 i…

Python 导入Excel三维坐标数据 生成三维曲面地形图(体) 5-1、线条平滑曲面且可通过面观察柱体变化(一)

环境和包: 环境 python:python-3.12.0-amd64包: matplotlib 3.8.2 pandas 2.1.4 openpyxl 3.1.2 scipy 1.12.0 代码: import pandas as pd import matplotlib.pyplot as plt from mpl_toolkits.mplot3d import Axes3D from scipy.interpolate import griddata fr…

HAProxy 简单介绍

一 HAProxy介绍 &#xff08;一&#xff09;发展历史 HAProxy是法国开发者威利塔罗(Willy Tarreau)在2000年使用C语言开发的一个开源软件&#xff0c;是一款具备高并发(一万以上)、高性能的TCP和HTTP负载均衡器&#xff0c;支持基于cookie的持久性&#xff0c;自动故障切换…

GPT与R 在生态环境领域数据统计分析

原文链接&#xff1a;GPT与R 在生态环境领域数据统计分析https://mp.weixin.qq.com/s?__bizMzUzNTczMDMxMg&mid2247597092&idx2&sn0a7ac5cf03d37c7b4659f870a7b71a77&chksmfa823dc3cdf5b4d5ee96a928a1b854a44aff222c82b2b7ebb7ca44b27a621edc4c824115babe&…

软件杯 垃圾邮件(短信)分类算法实现 机器学习 深度学习

文章目录 0 前言2 垃圾短信/邮件 分类算法 原理2.1 常用的分类器 - 贝叶斯分类器 3 数据集介绍4 数据预处理5 特征提取6 训练分类器7 综合测试结果8 其他模型方法9 最后 0 前言 &#x1f525; 优质竞赛项目系列&#xff0c;今天要分享的是 &#x1f6a9; 垃圾邮件(短信)分类算…

实战案例——Kafka集群部署

1. 规划节点 IP主机名节点192.168.100.10zookeeper1集群节点192.168.100.20zookeeper2集群节点192.168.100.30zookeeper集群节点 2. 基础准备 使用ZooKeeper集群搭建的3个节点来构建Kafka集群&#xff0c;因为Kafka服务依赖于ZooKeeper服务&#xff0c; 所以不再多创建云主机…

打卡--MySQL8.0 二 (用户权限管理)

一、mysql8修改了安全规则&#xff0c;不能像mysql5.7 一次性创建用户并授权&#xff0c;需要分批创建。 1、注意在MySQL8.0版本中创建用户一定要在配置文件中增加如下内容&#xff0c;来兼容旧的程序运行。 default_authentication_pluginmysql_native_password 2、创建用户…

LM2904DT运算放大器中文资料规格书PDF数据手册引脚图参数图片功能概述

产品概述&#xff1a; 该电路由两个独立的高增益运算放大器&#xff08;运算放大器&#xff09;组成&#xff0c;内部实现了频率补偿。它们专为汽车和工业控制系统而设计。该电路采用单电源供电&#xff0c;工作电压范围很广。低功耗与电源电压的大小无关。 应用领域包括传感…

【力扣 - 和为K的子数组】

题目描述 给你一个整数数组 nums 和一个整数 k &#xff0c;请你统计并返回 该数组中和为 k 的子数组的个数 。 子数组是数组中元素的连续非空序列。 示例 1&#xff1a; 输入&#xff1a;nums [1,1,1], k 2 输出&#xff1a;2 示例 2&#xff1a; 输入&#xff1a;num…

ElementUI两个小坑

1.form表单绑定的是一个对象&#xff0c;表单里的一个输入项是对象的一个属性之一&#xff0c;修改输入项&#xff0c;表单没刷新的问题&#xff0c; <el-form :model"formData" :rules"rules" ref"editForm" class"demo-ruleForm"…

【机器学习】机器学习创建算法第1篇:机器学习算法课程定位、目标【附代码文档】

机器学习&#xff08;算法篇&#xff09;完整教程&#xff08;附代码资料&#xff09;主要内容讲述&#xff1a;机器学习算法课程定位、目标&#xff0c;K-近邻算法&#xff0c;1.1 K-近邻算法简介&#xff0c;1.2 k近邻算法api初步使用定位,目标,学习目标,1 什么是K-近邻算法,…

Java旋转矩阵

题目&#xff1a; 给你一幅由 N N 矩阵表示的图像&#xff0c;其中每个像素的大小为 4 字节。请你设计一种算法&#xff0c;将图像旋转 90 度。 不占用额外内存空间能否做到&#xff1f; 示例 1: 给定 matrix [ [1,2,3], [4,5,6], [7,8,9] ], 原地旋转输入矩阵&…

山姆・阿尔特曼重返OpenAI董事会;Car-GPT:LLMs能否最终实现自动驾驶?

&#x1f989; AI新闻 &#x1f680; 山姆・阿尔特曼重返OpenAI董事会 摘要&#xff1a;经历长达数月的审查后&#xff0c;山姆・阿尔特曼已重返OpenAI董事会&#xff0c;并作为返回条件之一&#xff0c;OpenAI还新增了三名外部女性董事会成员。这标志着公司正努力摆脱去年11…

开源模型应用落地-业务优化篇(八)

一、前言 在之前的学习中&#xff0c;我相信您已经学会了一些优化技巧&#xff0c;比如分布式锁、线程池优化、请求排队、服务实例扩容和消息解耦等等。现在&#xff0c;我要给您介绍最后一篇业务优化的内容了。这个优化方法是通过定时统计问题的请求频率&#xff0c;然后将一些…

交叉编译x264 zlib ffmpeg以及OpenCV等 以及解决交叉编译OpenCV时ffmpeg始终为NO的问题

文章目录 环境编译流程nasm编译x264编译zlib编译libJPEG编译libPNG编译libtiff编译 FFmpeg编译OpenCV编译问题1解决方案 问题2解决方案 总结 环境 系统&#xff1a;Ubutu 18.04交叉编译链&#xff1a;gcc-arm-10.2-2020.11-x86_64-aarch64-none-linux-gnu 我的路径/opt/toolch…
最新文章