简体   繁体   中英

WPF Drag Control during runtime

I been working with winforms, so my knowledge of WFP is non existent, this is something i am trying to test. In code I am generating few buttons and placing them on Canvas. Than after clik on any button, i am moving that button around, and after second click button should stay at the position where mouse cursor was when clicked.

If mouse cursor go outside canvas then button will stop follow it.

My problem is, that button is moving, but only when mouse cursor is over that button or any other control, but it is not moving while mouse cursor is traveling over Canvas.

XAML

<Window x:Class="WpfTestDrag.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        xmlns:local="clr-namespace:WpfTestDrag"
        mc:Ignorable="d"
        Title="MainWindow" Height="522" Width="909">
    <Grid>
        <Grid.ColumnDefinitions >
            <ColumnDefinition Width="20"/>
            <ColumnDefinition Width="130*"/>
            <ColumnDefinition Width="33*"/>
            <ColumnDefinition Width="120"/>
        </Grid.ColumnDefinitions>
        <Grid.RowDefinitions >
            <RowDefinition Height="40" />
            <RowDefinition Height="*" />
            <RowDefinition Height="20" />
        </Grid.RowDefinitions>

        <Canvas Grid.Column="1" Grid.Row="1" x:Name="cnvTest" Width="auto" Height="auto" PreviewMouseMove="CnvTest_PreviewMouseMove"/>
        <TextBlock x:Name="txbStatus" Grid.Column="1" Grid.Row="2" Grid.ColumnSpan="2"/>
    </Grid>
</Window>

C#

 public partial class MainWindow : Window
    {
        Button bts;
        Boolean  isUsed = false;
        public MainWindow()
        {
            InitializeComponent();

            CreateButtons();
        }

        private void CreateButtons()
        {
            var xPos = 10.0;
            var yPos = 15.0;
            var Rnd = new Random();

            for (int i = 0; i < 3; i++)
            {
                var btn = new Button();
                btn.Name = "btn" + i;
                btn.Content = "Button - " + i;
                btn.Tag = "Tag" + i;
                btn.Width = 150;
                btn.Height = 150;
                btn.Click += Btn_Click;

                Canvas.SetLeft(btn, xPos);
                Canvas.SetTop(btn, yPos);
                cnvTest.Children.Add(btn);

               xPos = xPos + btn.Width + Rnd.Next(-15,40);
               yPos = yPos + btn.Height + Rnd.Next(-15, 40);
            }
        }


        private void Btn_Click(object sender, RoutedEventArgs e)
        {
            bts = sender as Button;
           if (isUsed == false)
            {
                isUsed = true;
            }
           else
            {
                isUsed = false;
            }
        }

        private void CnvTest_PreviewMouseMove(object sender, MouseEventArgs e)
        {
            Point p = Mouse.GetPosition(cnvTest);

            if (isUsed == true)
            {
                Canvas.SetLeft(bts, p.X);
                Canvas.SetTop(bts, p.Y);
                txbStatus.Text = bts.Name.ToString() + " isUsed:" + isUsed.ToString() + " -> xPos:" + p.X.ToString() + " yPos:" + p.Y.ToString();
            }
        }


    }

Should I use something else than Canvas for this?

You should set the Background property of the Canvas to Transparent (or any other Brush ) for it to respond to the mouse events:

<Canvas Grid.Column="1" Grid.Row="1" x:Name="cnvTest" Width="auto" Height="auto" PreviewMouseMove="CnvTest_PreviewMouseMove"
        Background="Transparent"/>

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM