旋转后更改WPF元素的父级(设置新坐标问题)

时间:2016-06-25 12:07:12

标签: c# wpf xaml rotation position

我需要更改元素的父级。 (对于组/ ungroup形状) 但是如果元素有一个旋转,我就不能为元素设置新的位置。

我看到了thisthisthisthis页面以及许多其他方式,但都没有正常工作。

请参阅my sample project和以下图片:

enter image description here

Rect1的父级为ChildCanvas1Rect2的父级为ChildCanvas2,我想将Rect1Rect2移至MainCanvas。 (并删除ChildCanvasChildCanvas2

我对Rect1没有任何问题,因为它没有任何轮换。 但是Rect2有一个旋转(-20度),我无法正确设置它的新坐标。

请看这张图片:

enter image description here

如何在旋转后更改元素的父级并正确设置新坐标?

更新

注意我需要一般方法(对于大型应用中的group / ungroup元素,每个元素(可能)都有TranslateTransformSkewTransform以及RotateTransformScaleTransform

XAML:

<Canvas x:Name="MainCanvas">
    <Canvas x:Name="ChildCanvas1" Width="500" Height="250" Background="Bisque" Canvas.Top="54">
        <Rectangle x:Name="Rect1" Width="200" Height="100" Fill="Red" Canvas.Left="150" Canvas.Top="100"/>
    </Canvas>

    <Canvas Name="ChildCanvas2" Width="500" Height="250" Background="Bisque" Canvas.Left="516" Canvas.Top="54">
        <Rectangle Name="Rect2" Width="200" Height="100" Fill="Red" Canvas.Left="150" Canvas.Top="100">
              <Rectangle.RenderTransform>
                <TransformGroup>
                    <SkewTransform AngleX="-40"/>
                <RotateTransform Angle="-20"/>
                </TransformGroup>
            </Rectangle.RenderTransform>
        </Rectangle>
    </Canvas>
    <Button Name="btn1" Click="btn1_Click" Content="Move Rect1 to MainCanvas and Remove ChildCanvas1" Width="356" Height="30" Canvas.Left="59" Canvas.Top="310"/>
    <Button Name="btn2"  Click="btn2_Click" Content="Move Rect2 to MainCanvas and Remove ChildCanvas2" Width="350" Height="30" Canvas.Left="590" Canvas.Top="310"/>

C#代码:

GeneralTransform transform = Rect2.TransformToVisual(MainCanvas);
Rect rect = transform.TransformBounds(new Rect(0, 0, Rect2.Width, Rect2.Height));
double ChildCanvas2Left = Canvas.GetLeft(ChildCanvas2);
double ChildCanvas2Top = Canvas.GetLeft(ChildCanvas2);
ChildCanvas2.Children.Remove(Rect2);
MainCanvas.Children.Add(Rect2);
Canvas.SetLeft(Rect2, rect.Left);
Canvas.SetTop(Rect2, rect.Top);
MainCanvas.Children.Remove(ChildCanvas2);

2 个答案:

答案 0 :(得分:4)

Rect2移至Rect2后,您需要重新计算MainCanvas。像这样:

Canvas.SetTop(Rect2, Canvas.GetTop(Rect2) + Canvas.GetTop(ChildCanvas2));

完整的代码:

private void btn2_Click(object sender, RoutedEventArgs e)
{       
    GeneralTransform transform = Rect2.TransformToVisual(MainCanvas);
    Rect rect = transform.TransformBounds(new Rect(0, 0, Rect2.Width, Rect2.Height));
    ChildCanvas2.Children.Remove(Rect2);
    MainCanvas.Children.Remove(ChildCanvas2);
    Canvas.SetLeft(Rect2, rect.Left);
    Canvas.SetTop(Rect2, Canvas.GetTop(Rect2) + Canvas.GetTop(ChildCanvas2));
    MainCanvas.Children.Add(Rect2);      
}

但是,在您的情况下,Rect2.TransformToVisualtransform.TransformBounds不是必需的,如果没有它们,您可以更清洁,更轻松地获得相同的结果。像这样:

ChildCanvas2.Children.Remove(Rect2);
MainCanvas.Children.Remove(ChildCanvas2);
Canvas.SetLeft(Rect2, Canvas.GetLeft(Rect2) + Canvas.GetLeft(ChildCanvas2));
Canvas.SetTop(Rect2, Canvas.GetTop(Rect2) + Canvas.GetTop(ChildCanvas2));
MainCanvas.Children.Add(Rect2); 

编辑:一般方式:

ChildCanvas2.Children.Remove(Rect2);
MainCanvas.Children.Remove(ChildCanvas2);
Canvas.SetLeft(Rect2, Canvas.GetLeft(Rect2) + Canvas.GetLeft(ChildCanvas2));
Canvas.SetTop(Rect2, Canvas.GetTop(Rect2) + Canvas.GetTop(ChildCanvas2));
Canvas.SetRight(Rect2, Canvas.GetRight(Rect2) + Canvas.GetRight(ChildCanvas2));
Canvas.SetBottom(Rect2, Canvas.GetBottom(Rect2) + Canvas.GetBottom(ChildCanvas2));
MainCanvas.Children.Add(Rect2);  

答案 1 :(得分:2)

我已将RenderTransform更改为LayoutTransform的{​​{1}}:

Rect2

现在<Rectangle Name="Rect2" Width="200" Height="100" Fill="Red" Canvas.Left="150" Canvas.Top="100"> <Rectangle.LayoutTransform> <RotateTransform Angle="-20"/> </Rectangle.LayoutTransform> </Rectangle> 如下所示:

enter image description here

当我按下第二个按钮时,我看到了这个结果:

enter image description here

因此,Rect2保持原始位置。