canvas 缩放时在不同点绘制的矩形
rectangle drawn in different point when canvas is zoomed
我有一个canvas,它有缩放功能。它里面有很多元素,所以为了选择,我打算使用一个选择框,当点击选择框时我会动态创建它。单击按钮时,我将矩形添加到 canvas 中,再次单击按钮时,我将其删除。
我有以下 xaml 代码:
<Viewbox x:Name="vbCanvas">
<Grid x:Name="theGrid"
MouseDown="Grid_MouseDown"
MouseUp="Grid_MouseUp"
MouseMove="Grid_MouseMove"
Background="Transparent">
<Canvas Name="canvasWaSNA" Margin="0,10,10,10" Height="720" Width="1280">
</Canvas>
</Grid>
</Viewbox>
theGrid
的鼠标事件在 canvas 的运行时绘制矩形。这些事件的代码是:
bool mouseDown = false;
Point mouseDownPos;
Point mouseUpPos;
private void Grid_MouseDown(object sender, MouseButtonEventArgs e)
{
mouseDown = true;
mouseDownPos = e.GetPosition(theGrid);
theGrid.CaptureMouse();
// Initial placement of the drag selection box.
Canvas.SetLeft(sBox, mouseDownPos.X);
Canvas.SetTop(sBox, mouseDownPos.Y);
sBox.Width = 0;
sBox.Height = 0;
// Make the drag selection box visible.
sBox.Visibility = Visibility.Visible;
}
}
private void Grid_MouseUp(object sender, MouseButtonEventArgs e)
{
// Release the mouse capture and stop tracking it.
mouseDown = false;
mouseUpPos = e.GetPosition(theGrid);
theGrid.ReleaseMouseCapture();
// Show the drag selection box.
sBox.Visibility = Visibility.Visible;
MessageBox.Show(mouseDownPos.ToString() + " " + mouseUpPos.ToString());
}
private void Grid_MouseMove(object sender, MouseEventArgs e)
{
if (mouseDown)
{
// When the mouse is held down, reposition the drag selection box.
Point mousePos = e.GetPosition(theGrid);
if (mouseDownPos.X < mousePos.X)
{
Canvas.SetLeft(sBox, mouseDownPos.X);
sBox.Width = mousePos.X - mouseDownPos.X;
}
else
{
Canvas.SetLeft(sBox, mousePos.X);
sBox.Width = mouseDownPos.X - mousePos.X;
}
if (mouseDownPos.Y < mousePos.Y)
{
Canvas.SetTop(sBox, mouseDownPos.Y);
sBox.Height = mousePos.Y - mouseDownPos.Y;
}
else
{
Canvas.SetTop(sBox, mousePos.Y);
sBox.Height = mouseDownPos.Y - mousePos.Y;
}
}
}
要在运行时创建一个矩形,我必须单击一个按钮。该按钮的事件如下:
private void select_Click_1(object sender, RoutedEventArgs e)
{
if (!canvasWaSNA.Children.Contains(sBox))
{
sBox.Name = "selectionBox";
sBox.StrokeThickness = 1.5 / zoomfactor;
sBox.StrokeDashArray = new DoubleCollection { 1, 2 };
sBox.Visibility = System.Windows.Visibility.Collapsed;
sBox.Stroke = Brushes.Gray;
canvasWaSNA.Children.Add(sBox);
}
else
{
sBox.Visibility = System.Windows.Visibility.Collapsed;
canvasWaSNA.Children.Remove(sBox);
}
}
我正在使用以下代码放大 canvas:
double zoomfactor = 1.0;
void window_MouseWheel(object sender, MouseWheelEventArgs e)
{
Point p = e.MouseDevice.GetPosition(canvasWaSNA); //gets the location of the canvas at which the mouse is pointed
Matrix m = canvasWaSNA.RenderTransform.Value;
if (e.Delta > 0)
{ //the amount of wheel of mouse changed. e.Delta holds int value.. +ve for uproll and -ve for downroll
m.ScaleAtPrepend(1.1, 1.1, p.X, p.Y);
zoomfactor *= 1.1;
}
else
{
m.ScaleAtPrepend(1 / 1.1, 1 / 1.1, p.X, p.Y);
zoomfactor /= 1.1;
}
canvasWaSNA.RenderTransform = new MatrixTransform(m);
}
当我的canvas为原始尺寸时,矩形绘制完美,但当我放大或缩小时,矩形绘制异常。它从其他点开始绘制。可能是什么问题?请帮助
嗯,我不应该捕获鼠标相对于 theGrid
的位置,因为我必须创建相对于 canvas 的矩形。因此,我必须获得 e.GetPosition(canvasWaSNA)
的位置并显示预期的结果。它捕获了 canvas 上的鼠标位置。现在,即使放大或缩小矩形也能完美绘制。
此外,我通过使用 canvas.
的缩放因子引用它来改进绘制的矩形的 StrokeThickness
private void Grid_MouseDown(object sender, MouseButtonEventArgs e)
{mouseDown = true;
mouseDownPos = e.GetPosition(canvasWaSNA);
theGrid.CaptureMouse();
sBox.StrokeThickness = 1.5 / zoomfactor;
// Initial placement of the drag selection box.
Canvas.SetLeft(sBox, mouseDownPos.X);
Canvas.SetTop(sBox, mouseDownPos.Y);
sBox.Width = 0;
sBox.Height = 0;
// Make the drag selection box visible.
sBox.Visibility = Visibility.Visible;
}
我有一个canvas,它有缩放功能。它里面有很多元素,所以为了选择,我打算使用一个选择框,当点击选择框时我会动态创建它。单击按钮时,我将矩形添加到 canvas 中,再次单击按钮时,我将其删除。 我有以下 xaml 代码:
<Viewbox x:Name="vbCanvas">
<Grid x:Name="theGrid"
MouseDown="Grid_MouseDown"
MouseUp="Grid_MouseUp"
MouseMove="Grid_MouseMove"
Background="Transparent">
<Canvas Name="canvasWaSNA" Margin="0,10,10,10" Height="720" Width="1280">
</Canvas>
</Grid>
</Viewbox>
theGrid
的鼠标事件在 canvas 的运行时绘制矩形。这些事件的代码是:
bool mouseDown = false;
Point mouseDownPos;
Point mouseUpPos;
private void Grid_MouseDown(object sender, MouseButtonEventArgs e)
{
mouseDown = true;
mouseDownPos = e.GetPosition(theGrid);
theGrid.CaptureMouse();
// Initial placement of the drag selection box.
Canvas.SetLeft(sBox, mouseDownPos.X);
Canvas.SetTop(sBox, mouseDownPos.Y);
sBox.Width = 0;
sBox.Height = 0;
// Make the drag selection box visible.
sBox.Visibility = Visibility.Visible;
}
}
private void Grid_MouseUp(object sender, MouseButtonEventArgs e)
{
// Release the mouse capture and stop tracking it.
mouseDown = false;
mouseUpPos = e.GetPosition(theGrid);
theGrid.ReleaseMouseCapture();
// Show the drag selection box.
sBox.Visibility = Visibility.Visible;
MessageBox.Show(mouseDownPos.ToString() + " " + mouseUpPos.ToString());
}
private void Grid_MouseMove(object sender, MouseEventArgs e)
{
if (mouseDown)
{
// When the mouse is held down, reposition the drag selection box.
Point mousePos = e.GetPosition(theGrid);
if (mouseDownPos.X < mousePos.X)
{
Canvas.SetLeft(sBox, mouseDownPos.X);
sBox.Width = mousePos.X - mouseDownPos.X;
}
else
{
Canvas.SetLeft(sBox, mousePos.X);
sBox.Width = mouseDownPos.X - mousePos.X;
}
if (mouseDownPos.Y < mousePos.Y)
{
Canvas.SetTop(sBox, mouseDownPos.Y);
sBox.Height = mousePos.Y - mouseDownPos.Y;
}
else
{
Canvas.SetTop(sBox, mousePos.Y);
sBox.Height = mouseDownPos.Y - mousePos.Y;
}
}
}
要在运行时创建一个矩形,我必须单击一个按钮。该按钮的事件如下:
private void select_Click_1(object sender, RoutedEventArgs e)
{
if (!canvasWaSNA.Children.Contains(sBox))
{
sBox.Name = "selectionBox";
sBox.StrokeThickness = 1.5 / zoomfactor;
sBox.StrokeDashArray = new DoubleCollection { 1, 2 };
sBox.Visibility = System.Windows.Visibility.Collapsed;
sBox.Stroke = Brushes.Gray;
canvasWaSNA.Children.Add(sBox);
}
else
{
sBox.Visibility = System.Windows.Visibility.Collapsed;
canvasWaSNA.Children.Remove(sBox);
}
}
我正在使用以下代码放大 canvas:
double zoomfactor = 1.0;
void window_MouseWheel(object sender, MouseWheelEventArgs e)
{
Point p = e.MouseDevice.GetPosition(canvasWaSNA); //gets the location of the canvas at which the mouse is pointed
Matrix m = canvasWaSNA.RenderTransform.Value;
if (e.Delta > 0)
{ //the amount of wheel of mouse changed. e.Delta holds int value.. +ve for uproll and -ve for downroll
m.ScaleAtPrepend(1.1, 1.1, p.X, p.Y);
zoomfactor *= 1.1;
}
else
{
m.ScaleAtPrepend(1 / 1.1, 1 / 1.1, p.X, p.Y);
zoomfactor /= 1.1;
}
canvasWaSNA.RenderTransform = new MatrixTransform(m);
}
当我的canvas为原始尺寸时,矩形绘制完美,但当我放大或缩小时,矩形绘制异常。它从其他点开始绘制。可能是什么问题?请帮助
嗯,我不应该捕获鼠标相对于 theGrid
的位置,因为我必须创建相对于 canvas 的矩形。因此,我必须获得 e.GetPosition(canvasWaSNA)
的位置并显示预期的结果。它捕获了 canvas 上的鼠标位置。现在,即使放大或缩小矩形也能完美绘制。
此外,我通过使用 canvas.
StrokeThickness
private void Grid_MouseDown(object sender, MouseButtonEventArgs e)
{mouseDown = true;
mouseDownPos = e.GetPosition(canvasWaSNA);
theGrid.CaptureMouse();
sBox.StrokeThickness = 1.5 / zoomfactor;
// Initial placement of the drag selection box.
Canvas.SetLeft(sBox, mouseDownPos.X);
Canvas.SetTop(sBox, mouseDownPos.Y);
sBox.Width = 0;
sBox.Height = 0;
// Make the drag selection box visible.
sBox.Visibility = Visibility.Visible;
}