[C#] [WPF] 在MVVM中实现拖拽功能 - 入门

news/2024/9/21 4:28:55

拖拽功能是使用频率较高的一种交互, 用传统方法去写很简单, 但是在mvvm规则下, 也没必要弄得很麻烦
我的入门案例就选择了使用mvvm重写tutorialspoint - Interaction里的调色盘案例, view如下
image

MainWindow.xaml

这里的重点是控件要允许拖拽以及对应的事件
目标控件, 填充色绑定, 允许drop, drop方法

<!-- #region target-->
<RectangleAllowDrop="True"Drop="TargetRect_Drop"Fill="{Binding FillColor}"/>
<!--#endregion-->

来源控件, 因为要拖动, 所以用MouseMove

<!--#region source-->
<RectangleFill="Beige"MouseMove="SourceRect_MouseMove" />
<!--#endregion-->

MainWindow.xaml.cs

在这里, 就是写事件的主要逻辑
1️⃣ 首先, 设置一个全局变量

MainWindowViewModel MainVM;

2️⃣然后写方法

// drop方法
private void TargetRect_Drop(object sender, DragEventArgs e)
{// GetDataPresent: 检查e.Data是否可以转换为string格式来存储if (e.Data.GetDataPresent(DataFormats.StringFormat)){// GetData: 将数据转化为string格式, 注意将DataObject类型强制转为stringstring color = (string)e.Data.GetData(DataFormats.StringFormat);// 赋值MainVM.FillColor = color;//MainVM.FillColorName = (Color)ColorConverter.ConvertFromString(MainVM.FillColor);}
}

然后是MouseMove

// drag方法: 鼠标左键点击并拖动时触发, 因为要拖动,所以需要一个MouseMove事件
private void SourceRect_MouseMove(object sender, MouseEventArgs e)
{// 按下左键if (e.LeftButton == MouseButtonState.Pressed){// 指定senderRectangle source = sender as Rectangle;// 拖动方法DargDrop.DoDragDropDragDrop.DoDragDrop(source, source.Fill.ToString(), DragDropEffects.Copy);}
}

MainViewModel.cs

简简单单声明一下要用的变量

[ObservableProperty]
private string _fillColor = "AliceBlue";

关于DragDrop.DoDragDrop

应该是拖拽行为中比较重要的方法(看了好多都是用这个)
官方文档: https://learn.microsoft.com/en-us/dotnet/api/system.windows.dragdrop.dodragdrop?view=windowsdesktop-8.0

⭐省流: 意思就是这个方法需要指定来源, 传输的数据还有效果, 数据会被自动封装 (目标引用数据的话可以用e.Data.GetData啥的), 返回的就是传入的拖拽效果enum值⭐

用处: 启动一次拖拽行为

// 如果dragSource或data为null, 则报错
public static System.Windows.DragDropEffects DoDragDrop (System.Windows.DependencyObject dragSource, object data, System.Windows.DragDropEffects allowedEffects);

参数:
dragSource ➡️ 指代被拖拽的对象
data ➡️ 包含传输数据的data对象
allowedEffects ➡️ 行为中允许的拖拽效果, 来自DragDropEffects之中的某个值

返回: 拖拽行为中最终效果, 同样来自DragDropEffects

DragDrop.DoDragDrop(source, source.Fill.ToString(), DragDropEffects.Copy)

source代表被拖拽的控件/对象, 传输的是source的Fill属性, 并且会被自动封装进DataObject中

DragDropEffects - Enum
(不想写了了直接放图)
image

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

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

相关文章

K8S之yaml 文件详解pod、deployment、service(转)

原文:https://blog.csdn.net/footless_bird/article/details/125946101 作者:墨鸦_Cormorant 来源:CSDNK8S中的 yaml 文件 yaml语法学习Kubernetes 支持 YAML 和 JSON格式 管理资源对象JSON 格式:主要用于 api 接口之间消息的传递YAML 格式:用于配置和管理,YAML是一种简洁…

Rocky Linux 9.4 正式版发布 - RHEL 100% 1:1 兼容免费发行版

Rocky Linux 9.4 正式版发布 - RHEL 100% 1:1 兼容免费发行版Rocky Linux 9.4 正式版发布 - RHEL 100% 1:1 兼容免费发行版 Rocky Linux 由 CentOS 项目的创始人 Gregory Kurtzer 领导 请访问原文链接:Rocky Linux 9.4 正式版发布 - RHEL 100% 1:1 兼容免费发行版,查看最新版…

python算法:年龄问题

一,认识递归函数 1,什么是递归?递归的工作原理是,如果函数需要处理的问题大小合适,则直接求解并返回结果,否则将问题分解成两个或多个更小的子问题,并对子问题进行相同的处理,直到问题无法分解为止 2,什么是递归函数:递归函数(recursive function)是指在函数体中可以…

Nginx配置https(证书)报错

一、nginx配置问题 nginx配置https的时候报错:nginx: [emerg]unknown directive35+GAN "ssl" in /usr/local/nginx/conf/nginx.conf:28  或者nginx: [emerg] the "ssl" parameter requires ngx_http_ssl_module in /usr/loca.... 出现这个问题的时候可以…

如何基于原名称批量重命名(格式化)文件(夹)名

首先,需要用到的这个工具:度娘网盘 提取码:qwu2 蓝奏云 提取码:2r1z 现在需要把这些文档的文件名处理,格式为:4位数字 - 6位数字 - 10位数字,办法如下: 打开工具 切换到 文件批量复制 模块,快捷键如图找到右下角的 重命名 按钮,点开把要处理的这些文件拖入进去(如…

python算法:谁在说谎?

一,for循环: 1,功能:重复执行同一段代码语法: for index in range(n): # 循环体代码 index : 用来依次接收可迭代对象中的元素的变量名range()函数:负责返回整数序列 流程图:2,应用 range可以同时指定start 和stop,用for遍历并打印1 2 3 4# 指定 start和stop # print的参数 e…

无规律快速批量重命名文件(夹)-固定命名

首先,需要用到的这个工具:度娘网盘 提取码:qwu2 蓝奏云 提取码:2r1z 这里有1万多个文件,要命名成无规律的、不同的文件名 目标文件名里面的是上面已经修正数据的目标 一句话思路:提取全部目标名称,放到要改动的地方去 打开工具,切换到“文件批量复制” 借助这个版块…

python算法: 棋盘上的麦粒(舍罕王赏麦)

一,for循环: 1,功能:重复执行同一段代码语法: for index in range(n): # 循环体代码 index : 用来依次接收可迭代对象中的元素的变量名range()函数:负责返回整数序列 流程图:2,应用 range可以同时指定start 和stop,用for遍历并打印1 2 3 4# 指定 start和stop # print的参数 e…