我正在使用wpf为绘图程序中的一行编写装饰程序。这条线是在代码后面绘制的,然后用名为LineAdorner的自定义装饰器进行装饰。我设法用一个Thumb作为这条线的起点和终点。我的问题是关于起点和终点的拇指排列。我认为问题出在ArrangeOverride方法中,这里应该用起点和终点来排列拇指。在RectXY参数中,我找不到要减去或添加的正确数量。如何找到这些值以始终将拇指与直线的点排列在一起?
来自自定义装饰程序的代码如下:
public class LineAdorner : Adorner{ private Point start; private Point end; private Thumb startThumb; private Thumb endThumb; private Line selectedLine; private VisualCollection visualChildren; // Constructor public LineAdorner(UIElement adornedElement) : base(adornedElement) { visualChildren = new VisualCollection(this); startThumb = new Thumb { Cursor = Cursors.Hand, Width = 10, Height = 10, Background = Brushes.Green }; endThumb = new Thumb { Cursor = Cursors.Hand, Width = 10, Height = 10, Background = Brushes.BlueViolet }; startThumb.DragDelta += StartDragDelta; endThumb.DragDelta += EndDragDelta; visualChildren.Add(startThumb); visualChildren.Add(endThumb); selectedLine = AdornedElement as Line; } // Event for the Thumb Start Point private void StartDragDelta(object sender, DragDeltaEventArgs e) { Point position = Mouse.GetPosition(this); selectedLine.X1 = position.X; selectedLine.Y1 = position.Y; } // Event for the Thumb End Point private void EndDragDelta(object sender, DragDeltaEventArgs e) { Point position = Mouse.GetPosition(this); selectedLine.X2 = position.X; selectedLine.Y2 = position.Y; } protected override int VisualChildrenCount { get { return visualChildren.Count; } } protected override Visual GetVisualChild(int index) { return visualChildren[index]; } protected override void OnRender(DrawingContext drawingContext) { if (AdornedElement is Line) { selectedLine = AdornedElement as Line; start = new Point(selectedLine.X1, selectedLine.Y1); end = new Point(selectedLine.X2, selectedLine.Y2); } } protected override Size ArrangeOverride(Size finalSize) { var startRect = new Rect(selectedLine.X1, selectedLine.Y1, ActualWidth, ActualHeight); startThumb.Arrange(startRect); var endRect = new Rect(selectedLine.X2, selectedLine.Y2, ActualWidth, ActualHeight); endThumb.Arrange(endRect); return finalSize; } }

最佳答案

在你的排列覆盖中试试这个。您可以去掉“start”和“end”变量,并且不需要重写onrender,因为如果您告诉它们需要的位置,您的拇指将呈现它们自己。

    protected override Size ArrangeOverride(Size finalSize)
{
    selectedLine = AdornedElement as Line;

    double left = Math.Min(selectedLine.X1, selectedLine.X2);
    double top = Math.Min(selectedLine.Y1, selectedLine.Y2);

    var startRect = new Rect(selectedLine.X1 - (startThumb.Width / 2), selectedLine.Y1 - (startThumb.Width / 2), startThumb.Width, startThumb.Height);
    startThumb.Arrange(startRect);

    var endRect = new Rect(selectedLine.X2 - (endThumb.Width / 2), selectedLine.Y2 - (endThumb.Height / 2), endThumb.Width, endThumb.Height);
    endThumb.Arrange(endRect);

    return finalSize;
}

您正在设置拇指的显式大小,因此必须在排列中保持该大小。此外,还需要减去拇指宽度和高度的一半,以使其在端点上居中。
由于画布和形状的性质,您需要减去线条的“真实”左上角值,因为与线条不同,装饰器不会从画布的左上角绘制自己。这不应该在使用画布之外被要求。

07-24 13:14