WPF - 放大滚动查看器内的图像,并使滚动条相应调整 [英] WPF - Zooming in on an image inside a scroll viewer, and having the scrollbars adjust accordingly

查看:1601
本文介绍了WPF - 放大滚动查看器内的图像,并使滚动条相应调整的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我已经整理了一个简单的WPF应用程序来演示我遇到的问题。我的XAML如下:

I have put together a simple WPF application to demonstrate the issue I am having. My XAML is below:

<Window x:Class="WpfApplication1.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        Title="MainWindow" Height="427" Width="467" Loaded="MainWindow_OnLoaded">
    <Grid>
        <ScrollViewer Name="MyScrollViewer" CanContentScroll="True">
            <Image Name="MyImage" HorizontalAlignment="Left" VerticalAlignment="Top" MouseWheel="UIElement_OnMouseWheel" MouseDown="MyImage_OnMouseDown" MouseUp="MyImage_OnMouseUp"/>
        </ScrollViewer>
    </Grid>
</Window>

代码隐藏如下:

using System;
using System.Windows;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;

namespace WpfApplication1
{
    /// <summary>
    /// Interaction logic for MainWindow.xaml
    /// </summary>
    public partial class MainWindow : Window
    {
        public MainWindow()
        {
            InitializeComponent();
        }

        private void UIElement_OnMouseWheel(object sender, MouseWheelEventArgs e)
        {
            var matrix = MyImage.RenderTransform.Value;

            if (e.Delta > 0)
            {
                matrix.ScaleAt(1.5, 1.5, e.GetPosition(this).X, e.GetPosition(this).Y);
            }
            else
            {
                matrix.ScaleAt(1.0 / 1.5, 1.0 / 1.5, e.GetPosition(this).X, e.GetPosition(this).Y);
            }

            MyImage.RenderTransform = new MatrixTransform(matrix);
        }

        private WriteableBitmap writeableBitmap;

        private void MainWindow_OnLoaded(object sender, RoutedEventArgs e)
        {
            var image = new WriteableBitmap(new BitmapImage(new Uri(@"C:\myImage.png", UriKind.Absolute)));

            MyImage.Width = image.Width;
            MyImage.Height = image.Height;

            image = BitmapFactory.ConvertToPbgra32Format(image);

            writeableBitmap = image;

            MyImage.Source = image;
        }

        private Point downPoint;
        private Point upPoint;

        private void MyImage_OnMouseDown(object sender, MouseButtonEventArgs e)
        {
            downPoint = e.GetPosition(MyImage);
        }

        private void MyImage_OnMouseUp(object sender, MouseButtonEventArgs e)
        {
            upPoint = e.GetPosition(MyImage);

            writeableBitmap.DrawRectangle(Convert.ToInt32(downPoint.X), Convert.ToInt32(downPoint.Y), Convert.ToInt32(upPoint.X), Convert.ToInt32(upPoint.Y), Colors.Red);
            MyImage.Source = writeableBitmap;
        }
    }
}

我已经使用Nuget添加了WriteableBitmapEx 。如果你运行它,并将 myImage.png 替换为计算机上实际图像的位置,你会发现一个如下所示的应用程序:

I have added WriteableBitmapEx using Nuget. If you run this, and replace myImage.png with the location of an actual image on your computer, you will find an application that looks something like this:

你可以画一个通过单击您希望框移动到的位置左上方的图像框,然后拖动到您希望框移动到的右下角,您将获得一个红色矩形。您甚至可以使用鼠标中键放大,并向上绘制一个矩形以获得更高的精度,这可以正常工作。

You can draw a box on the image by clicking on the top-left of where you want the box to go and dragging to the bottom right of where you want the box to go, you get a red rectangle. You can even zoom in with the middle-mouse, and draw a rectangle up close for more precision, this works as expected.

问题是,滚动时使用鼠标中键,滚动条不会重新调整,这是我正在创建的程序的要求。我的问题是当图像放大时如何强制滚动查看器上的滚动条重新调整?

The problem is that, when you scroll in with the middle mouse, the scroll bars don't re-adjust, which is a requirement of the program I am creating. My question is how do I force the scrollbars on the scrollviewer to re-adjust when the image is zoomed in?

我确信它与RenderTransform属性有关ScrollViewer,我需要更新它同时更新图像的RenderTransform属性(在UIElement_OnMouseWheel上),但我不确定如何去做。

I am convinced it has something to do with the RenderTransform property of the ScrollViewer, and that I need to update it at the same time I update the RenderTransform property of the image (on UIElement_OnMouseWheel) but I am unsure of exactly how to go about this.

推荐答案

您应该使用 LayoutTransform 而不是 RenderTransform 图片。

You should be using LayoutTransform instead of RenderTransform on your Image.

RenderTransform 在布局完成后发生,仅供视觉使用。 LayoutTransform 在布局传递之前完成,因此可以通知新尺寸的 ScrollViewer

RenderTransform happens after layout completes and is visual only. LayoutTransform is done before the layout pass and so can notify the ScrollViewer of the new size.

有关详细信息,请参阅此处: http://msdn.microsoft.com/en-us/library/system.windows.frameworkelement.layouttransform.aspx

See here for more info: http://msdn.microsoft.com/en-us/library/system.windows.frameworkelement.layouttransform.aspx

这篇关于WPF - 放大滚动查看器内的图像,并使滚动条相应调整的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆