Eggi Eggi - 2 months ago 47
C# Question

Scale canvas to mouse position

I am trying to implement a zoom-functionality for a canvas using the mouse wheel.
Currently I am just Zooming to the center position of the canvas using CenterX="0.5" and CenterY="0.5".
I would like to change the behavior so that the zooming happens at the mouse position and I would like to know if this is possible with a ScaleTransform.

Currently I use the following code:

<Canvas Width="500" Height="500">
<Canvas.LayoutTransform>
<ScaleTransform CenterX="0.5" CenterY="0.5"
ScaleX="{Binding Zoom}"
ScaleY="{Binding Zoom}" />
</Canvas.LayoutTransform>
</Canvas>

Answer

A very basic approach to zoom a Canvas (or any other UIElement) at a specific position would be to use a MatrixTransform for the RenderTransform property

<Canvas Width="500" Height="500" MouseWheel="Canvas_MouseWheel">
    <Canvas.RenderTransform>
        <MatrixTransform/>
    </Canvas.RenderTransform>
</Canvas>

and update the Matrix property of the transform like in this MouseWheel handler:

private void Canvas_MouseWheel(object sender, MouseWheelEventArgs e)
{
    var element = sender as UIElement;
    var position = e.GetPosition(element);
    var transform = element.RenderTransform as MatrixTransform;
    var matrix = transform.Matrix;
    var scale = e.Delta >= 0 ? 1.1 : (1.0 / 1.1); // choose appropriate scaling factor

    matrix.ScaleAtPrepend(scale, scale, position.X, position.Y);
    transform.Matrix = matrix;
}