【问题标题】:Image control and Image resizing when Stretch is set to Uniform拉伸设置为均匀时的图像控制和图像大小调整
【发布时间】:2015-03-14 10:01:48
【问题描述】:

我有这个特殊的问题。我有一个用户控件。我正在为 Windows 8.1 制作一个应用程序,我将从我的图片库中选择一个图像。图像将在我的应用程序中打开,拉伸是均匀的,水平和垂直对齐到中心。

我的用户控件将出现在我点击图像的位置。现在的问题是,当图像 Stretch 没有时,我能够放大正确的区域(在我的点击周围),但是现在当我将其 Stretch 设置为 Uniform 并且将 horizo​​ntal and vertical Alignment 设置为 Center ,我在我的用户控件中获取其他像素信息。

我想知道如何修复它。无论如何,图像也可以是 2*Full HD,也可以是 HD 甚至更低。 其次,我想知道图像的边界。有了边界,我想说的是,我的用户控件不应该超出图像的边界。 如何实现。如果需要我的代码,我会粘贴它,如果需要。

有这个video 供参考。这就是我要发展的!我已经准备好用户控件,并且我得到了 Stretch=NONE 的精确像素,并且没有设置水平和垂直对齐方式。

这是我的app代码

【问题讨论】:

  • 能否提供一些示例代码/xaml?
  • 查看代码。我已经在“app”这个词中链接了我的应用代码。
  • @RicoSuter 你能看到问题还是我应该重新发送代码?

标签: c# xaml image-processing windows-rt


【解决方案1】:

我认为问题在于您如何使用控件,而不是图像。如果您避免进行位图裁剪和替换,它将显着加快速度,并且可能适用于所有拉伸类型。

我已修改源以显示这一点 - 完全删除裁剪。如果您出于其他原因需要裁剪,则应考虑使用 unsafe 关键字(以及允许的属性设置)以显着加快其使用速度。

另外,为了避免滞后/向上跳跃,我添加了 IsHitTestVisible="False" 这样您的增量就不会因悬停在您的图像上而被打断。

我看到你已经有了 45 度代码 - 因为它不在你的源代码中,所以我只添加了一个 90 度旋转的示例,当你走到两边时 - 这样你就可以看到如何设置 RenderTransformOrigin 点。

MainPage.xaml:

<Page x:Name="page1" 
    x:Class="controlMagnifier.MainPage"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:local="using:controlMagnifier"
    xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
    xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
    mc:Ignorable="d">

    <Grid x:Name="ParentGrid" Background="{ThemeResource ApplicationPageBackgroundThemeBrush}" PointerReleased="ParentGrid_OnPointerReleased"  >
        <Canvas x:Name="InkPresenter" Height="auto" Width="auto">

            <Image Stretch="Uniform" x:Name="image2"  >
                <Image.Source >
                    <BitmapImage UriSource="/Assets/wallpaper.jpg" />
                </Image.Source>
            </Image>

        </Canvas>

        <local:MagnifierUsercontrol  x:Name="MagnifyTip"  Visibility="Collapsed"  ManipulationMode="All"
                                     IsHitTestVisible="False" Height="227" Width="171"
                                     VerticalContentAlignment="Bottom" HorizontalContentAlignment="Center">
        </local:MagnifierUsercontrol>
    </Grid>
</Page>

MainPage.xaml.cs:

using System;
using Windows.Foundation;
using Windows.Storage;
using Windows.UI.Input;
using Windows.UI.Xaml;
using Windows.UI.Xaml.Controls;
using Windows.UI.Xaml.Input;
using Windows.UI.Xaml.Media;
using Windows.UI.Xaml.Media.Imaging;

namespace controlMagnifier
{
    public sealed partial class MainPage : Page
    {
        public const int XAxis = 200;
        public const int YAxis = 435;
        private readonly RotateTransform myRotateTransform = new RotateTransform {CenterX = 0.5, CenterY = 1};
        private readonly ScaleTransform myScaleTransform = new ScaleTransform {ScaleX = 1, ScaleY = 1};
        private readonly TransformGroup myTransformGroup = new TransformGroup();
        private readonly TranslateTransform myTranslateTransform = new TranslateTransform();
        public WriteableBitmap CurrentBitmapObj, CurrentCroppedImage = null;
        public Point currentContactPt, GridPoint;
        public Thickness margin;
        public PointerPoint pt;
        public double xValue, yValue;

        public MainPage()
        {
            InitializeComponent();
            ParentGrid.Holding += Grid_Holding;
            image2.PointerMoved += InkCanvas_PointerMoved;
            image2.PointerReleased += ParentGrid_OnPointerReleased;
            margin = MagnifyTip.Margin;
            image2.CacheMode = new BitmapCache();

            myTransformGroup.Children.Add(myScaleTransform);
            myTransformGroup.Children.Add(myRotateTransform);
            myTransformGroup.Children.Add(myTranslateTransform);

            MagnifyTip.RenderTransformOrigin = new Point(0.5, 1);
            MagnifyTip.RenderTransform = myTransformGroup;
        }

        private void Grid_Holding(object sender, HoldingRoutedEventArgs e)
        {
            try
            {
                GridPoint = e.GetPosition(image2);

                myTranslateTransform.X = xValue - XAxis;
                myTranslateTransform.Y = yValue - YAxis;
                MagnifyTip.RenderTransform = myTransformGroup;

                MagnifyTip.Visibility = Visibility.Visible;
            }
            catch (Exception)
            {
                throw;
            }
        }

        private void InkCanvas_PointerMoved(object sender, PointerRoutedEventArgs e)
        {
            try
            {
                pt = e.GetCurrentPoint(image2);
                currentContactPt = pt.Position;

                xValue = currentContactPt.X;
                yValue = currentContactPt.Y;

                if (xValue > 300)
                {
                    myRotateTransform.Angle = -90;
                }
                else if (xValue < 100)
                {
                    myRotateTransform.Angle = 90;
                }
                else
                {
                    myRotateTransform.Angle = 0;
                }

                MagnifyTip.RenderTransform = myRotateTransform;

                myTranslateTransform.X = xValue - XAxis;
                myTranslateTransform.Y = yValue - YAxis;
                MagnifyTip.RenderTransform = myTransformGroup;
            }
            catch (Exception)
            {
                throw;
            }

            finally
            {
                e.Handled = true;
            }
        }

        private async void StoreCrrentImage()
        {
            try
            {
                var storageFile =
                    await
                        StorageFile.GetFileFromApplicationUriAsync(new Uri("ms-appx:///Assets/wallpaper.jpg",
                            UriKind.RelativeOrAbsolute));

                using (
                    var fileStream =
                        await storageFile.OpenAsync(FileAccessMode.Read))
                {
                    var bitmapImage = new BitmapImage();

                    await bitmapImage.SetSourceAsync(fileStream);
                    var writeableBitmap =
                        new WriteableBitmap(bitmapImage.PixelWidth, bitmapImage.PixelHeight);
                    fileStream.Seek(0);
                    await writeableBitmap.SetSourceAsync(fileStream);
                    CurrentBitmapObj = writeableBitmap;
                    writeableBitmap.Invalidate();
                }
            }
            catch (Exception)
            {
                // Graphics g=new Graphics();
                throw;
            }


            finally
            {
            }
        }

        private void ParentGrid_OnPointerReleased(object sender, PointerRoutedEventArgs e)
        {
            MagnifyTip.Visibility = Visibility.Collapsed;
        }
    }
}

放大镜用户控件.xaml:

<UserControl
    x:Class="controlMagnifier.MagnifierUsercontrol"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:local="using:controlMagnifier"
    xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
    xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
    mc:Ignorable="d" Height="227" Width="171">

    <Canvas x:Name="controlCanvas" x:FieldModifier="public"  Height="Auto" Width="Auto" >
        <Grid Height="227" Width="171" HorizontalAlignment="Center" Canvas.Left="0" Canvas.Top="0">

            <Border x:FieldModifier="public" x:Name="imgBorder" Width="150" CornerRadius="50,50,50,50" Margin="13,25,13,97">
                <Border.Background>
                    <ImageBrush x:FieldModifier="public" x:Name="image1"    />
                </Border.Background>
            </Border>

            <TextBlock x:Name="txtreading" Height="30" Width="80" Margin="0,-145,0,0" FontWeight="Bold" Foreground="Red"  FontSize="20" Text="ABC" TextAlignment="Center" />
            <!--<Image Height="120" Width="150" Margin="0,-50,0,0" Source="Assets/SmallLogo.scale-100.png" ></Image>-->
            <Path x:Name="MagnifyTip"  Data="M25.533,0C15.457,0,7.262,8.199,7.262,18.271c0,9.461,13.676,19.698,17.63,32.338    c0.085,0.273,0.34,0.459,0.626,0.457c0.287-0.004,0.538-0.192,0.619-0.467c3.836-12.951,17.666-22.856,17.667-32.33    C43.803,8.199,35.607,0,25.533,0z M25.533,32.131c-7.9,0-14.328-6.429-14.328-14.328c0-7.9,6.428-14.328,14.328-14.328    c7.898,0,14.327,6.428,14.327,14.328C39.86,25.702,33.431,32.131,25.533,32.131z" Fill="#FFF4F4F5" Stretch="Fill" Stroke="Black" UseLayoutRounding="False" Height="227" Width="171" />
        </Grid>
    </Canvas>

</UserControl>

让我知道这是否有帮助,或者是否对您的具体问题有进一步的帮助。

【讨论】:

  • 嗨,吉姆。谢谢回复。无论我在哪里移动鼠标,我都需要裁剪。我目前正在使用 WriteablebitmapEX 库进行裁剪。我只需要裁剪。请继续看视频。其次,你是否观察到控制来来往往的方式,动画,以及它转向屏幕末端的方式?我也需要帮助
  • 以及如何在裁剪功能中使用 unsafe 的任何想法。裁剪不像我在问题中附加的视频那样平滑。我需要它像视频一样流畅
  • XAML 中的图像控件,我需要它的水平和垂直对齐 = 居中。我没有尝试过你的代码,但这肯定会有所作为
  • 您是否需要裁剪以移动图标或放大背景?请为我重述问题 - 是图标定位问题还是背景的正确位置等?
  • 好的。请参阅,您有一个图像控件,其中 Stretch=Uniform 并且水平和垂直对齐设置为 Stretch。我的目标是用我的手指点击图像上的任何地方,一旦我点击,我的用户控件就会变得可见并在我的手指区域周围裁剪 50*50 像素。现在我还没有松开我的手指,我将它拖到图像上的其他位置,无论我的手指走到哪里,用户控件都会随着我移动并继续向我显示当前的裁剪区域。因此,如果我将手指从 x1 移动到 xn,裁剪后的图像将为 x1 ....xn
猜你喜欢
  • 2010-09-19
  • 1970-01-01
  • 1970-01-01
  • 2016-01-22
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2016-08-21
  • 2020-12-11
相关资源
最近更新 更多