Avalonia 实现平滑拖动指定控件

简介: Avalonia 实现平滑拖动指定控件

Avalonia 实现平滑拖动指定控件

1.创建一个UserControl控件,并且添加以下代码

using System;
using Avalonia;
using Avalonia.Controls;
using Avalonia.Input;
using Avalonia.Markup.Xaml;
using Avalonia.Media;
using Avalonia.Media.Imaging;
using Avalonia.Platform;
using Avalonia.Threading;
using Avalonia.VisualTree;

namespace Token;

/// <summary>
/// 实现拖动的控件
/// </summary>
public partial class DragControls : UserControl
{
   
   
    /// <summary>
    /// 记录上一次鼠标位置
    /// </summary>
    private Point lastMousePosition;

    /// <summary>
    /// 用于平滑更新坐标的计时器
    /// </summary>
    private DispatcherTimer _timer;

    /// <summary>
    /// 标记是否先启动了拖动
    /// </summary>
    private bool isDragging = false;

    /// <summary>
    /// 需要更新的坐标点
    /// </summary>
    private PixelPoint _targetPosition;

    public LoginStackPanelRight()
    {
   
   
        InitializeComponent();

        // 添加当前控件的事件监听
        PointerPressed += OnPointerPressed;
        PointerMoved += OnPointerMoved;
        PointerReleased += OnPointerReleased;

        // 初始化计时器
        _timer = new DispatcherTimer
        {
   
   
            Interval = TimeSpan.FromMilliseconds(10)
        };
        _timer.Tick += OnTimerTick;
    }

    /// <summary>
    /// 计时器事件
    /// </summary>
    /// <param name="sender"></param>
    /// <param name="e"></param>
    private void OnTimerTick(object sender, EventArgs e)
    {
   
   
        var window = this.FindAncestorOfType<Window>();
        if (window != null && window.Position != _targetPosition)
        {
   
   
            // 更新坐标
            window.Position = _targetPosition;
        }
    }

    private void InitializeComponent()
    {
   
   
        AvaloniaXamlLoader.Load(this);
    }

    private void OnPointerPressed(object sender, PointerPressedEventArgs e)
    {
   
   
        if (!e.GetCurrentPoint(this).Properties.IsLeftButtonPressed) return;
        // 启动拖动
        isDragging = true;
        // 记录当前坐标
        lastMousePosition = e.GetPosition(this);
        e.Handled = true;
        // 启动计时器
        _timer.Start();
    }

    private void OnPointerReleased(object sender, PointerReleasedEventArgs e)
    {
   
   
        if (!isDragging) return;
        // 停止拖动
        isDragging = false;
        e.Handled = true;
        // 停止计时器
        _timer.Stop();
    }

    private void OnPointerMoved(object sender, PointerEventArgs e)
    {
   
   
        if (!e.GetCurrentPoint(this).Properties.IsLeftButtonPressed) return;

        // 如果没有启动拖动,则不执行
        if (!isDragging) return;

        var currentMousePosition = e.GetPosition(this);
        var offset = currentMousePosition - lastMousePosition;
        var window = this.FindAncestorOfType<Window>();
        if (window != null)
        {
   
   
            // 记录当前坐标
            _targetPosition = new PixelPoint(window.Position.X + (int)offset.X,
                window.Position.Y + (int)offset.Y);
        }
    }
}

通过以上组件可以实现平滑拖动
效果如图

来着token的分享

目录
相关文章
|
算法 Windows
Winform控件优化之实现无锯齿的圆角窗体(或任意图形的无锯齿丝滑的窗体或控件)【借助LayeredWindow】
在一般能搜到的所有实现圆角窗体的示例中,都有着惨不忍睹的锯齿...而借助于Layered Windows,是可以实现丝滑无锯齿效果的Form窗体的,其具体原理就是分层窗体....
1849 0
Winform控件优化之实现无锯齿的圆角窗体(或任意图形的无锯齿丝滑的窗体或控件)【借助LayeredWindow】
|
9天前
|
图形学
Unity UGUI实现鼠标拖动图片
在 Unity UGUI 中实现鼠标拖动图片功能,主要涉及事件检测、坐标转换和物体位置更新。根据鼠标移动量更新图片位置。代码示例展示了如何通过这些步骤实现拖动效果。
|
9月前
|
前端开发 C# 容器
浅谈WPF之控件拖拽与拖动
使用过office的visio软件画图的小伙伴都知道,画图软件分为两部分,左侧图形库,存放各种图标,右侧是一个画布,将左侧图形库的图标控件拖拽到右侧画布,就会生成一个新的控件,并且可以自由拖动。那如何在WPF程序中,实现类似的功能呢?今天就以一个简单的小例子,简述如何在WPF中实现控件的拖拽和拖动,仅供学习分享使用,如有不足之处,还请指正。
232 2
|
C# 数据安全/隐私保护
ApeForms | C# WinForm窗体控件平滑减速运动
在桌面软件开发中,有时会需要控制窗体或控件移动以实现某些界面效果,比如幻灯片换页、侧面的展开栏等。 通常情况下我们会使用Timer以每隔一段时间修改一下坐标位置的方式来实现目标对象的位移效果,但通过这个方式实现的动效存在几个问题: 匀速运动效果生硬; 运动过程中不便灵活改变运动状态(如侧栏展开一半时令其收起); 动效多时需要创建多个Timer对象,不易管理且占用资源; ApeForms中为控件和窗体提供了平滑运动的扩展方法,很好的解决了这些问题。不仅是坐标的平滑运动,还有控件\窗体尺寸的平滑变化、透明度的平滑变化。允许在变化的中途随时更改目标坐标\尺寸\透明度,且使用共享的Timer
11426 1
WPF控件和窗体一起放大一起缩小
WPF控件和窗体一起放大一起缩小
274 0
|
C# 算法
在WPF中实现平滑滚动
原文:在WPF中实现平滑滚动 WPF实现滚动条还是比较方便的,只要在控件外围加上ScrollViewer即可,但美中不足的是:滚动的时候没有动画效果。在滚动的时候添加过渡动画能给我们的软件增色不少,例如Office 2013的滚动的时候支持动画看起来就舒服多了。
1542 0
Qt 隐藏标题栏可拖拽,自由缩放
Qt在隐藏标题栏的情况下,实现拖拽很简单,可以看这里https://blog.csdn.net/z609932088/article/details/80865742 或者这里:https://blog.csdn.net/z609932088/article/details/50898022
534 0
Qt 隐藏标题栏可拖拽,自由缩放
|
C#
WPF无边框拖动、全屏、缩放
原文:WPF无边框拖动、全屏、缩放 版权声明:本文为博主原创文章,转载请注明出处。 https://blog.csdn.net/lwwl12/article/details/78059361 先看效果 无边框 设置WindowStyle=”None”,窗口无关闭及缩放按钮,但还有黑边;设置AllowsTransparency=”True”,黑边没有了。
2148 0
|
C# Windows
使 WPF 支持触摸板的横向滚动
原文:使 WPF 支持触摸板的横向滚动 版权声明:本作品采用知识共享署名-非商业性使用-相同方式共享 4.0 国际许可协议进行许可。欢迎转载、使用、重新发布,但务必保留文章署名吕毅(包含链接:http://blog.csdn.net/wpwalter/),不得用于商业目的,基于本文修改后的作品务必以相同的许可发布。
1095 0
|
C# 前端开发
WPF 一个弧形手势提示动画
原文:WPF 一个弧形手势提示动画 这是一个操作提示动画,一个小手在屏幕上按照一个弧形来回运动 ...
735 0