1

在尝试构建图像裁剪器控件的 2 天令人沮丧之后,我转向 StackOverflow 寻找答案。

我正在将我的 WP8.0(Silverlight)应用程序移植到 WinRT(WP8.1 和 W8.1 的通用应用程序),我得到了所有内容......除了用户从图片库中选择图像的页面和它get 加载到页面上。然后用户可以移动图像或放大图像。有一个白色矩形边框是裁剪矩形(864px 605px - 这也应该是输出)。

做这个的最好方式是什么?加载的图像分辨率更高,所以我的猜测是将屏幕像素重新计算为图像像素。这段代码可以很好地翻译,但是当图像被缩放时,会有奇怪的偏移:

XAML:

<Path x:Name="SelectionPath" Stroke="Red" StrokeThickness="3" />

C#

public async void SetImage(StorageFile selectedFile)
    {
        Photo.ManipulationDelta += Composite_ManipulationDelta;
        compositeTranslation = new CompositeTransform();
        Photo.RenderTransform = this.compositeTranslation;
        Photo.ManipulationMode = ManipulationModes.TranslateX | ManipulationModes.TranslateY | ManipulationModes.Scale | ManipulationModes.Rotate;
        storageFile = selectedFile;



        storageFile = selectedFile;
        IRandomAccessStream inputStream = await selectedFile.OpenAsync(FileAccessMode.Read);

       var properties = await storageFile.Properties.GetImagePropertiesAsync();
       ImgWidth = properties.Width;


        BitmapImage tempImage = new BitmapImage();

        tempImage.SetSource(inputStream);
        Photo.Source = tempImage;
    }

    void Composite_ManipulationDelta(object sender, ManipulationDeltaRoutedEventArgs e)
    {
        // scale the image.
        compositeTranslation.CenterX = Photo.ActualWidth / 2;
        compositeTranslation.CenterY = Photo.ActualHeight / 2;
        compositeTranslation.ScaleX *= e.Delta.Scale;
        compositeTranslation.ScaleY *= e.Delta.Scale;
        compositeTranslation.TranslateX += e.Delta.Translation.X;
        compositeTranslation.TranslateY += e.Delta.Translation.Y;


        GeneralTransform transform = Photo.TransformToVisual(LayoutRoot);
        Point controlPosition = transform.TransformPoint(new Point(0, 0));

        int pointX = (int)controlPosition.X;
        int pointY = (int)controlPosition.Y;



    }
public async Task CropImage()
    {

        IBuffer data = await FileIO.ReadBufferAsync(storageFile);

        // create a stream from the file
        InMemoryRandomAccessStream ms = new InMemoryRandomAccessStream();
        DataWriter dw = new DataWriter(ms);
        dw.WriteBuffer(data);
        await dw.StoreAsync();
        ms.Seek(0);

        // find out how big the image is, don't need this if you already know
        BitmapImage bm = new BitmapImage();
        await bm.SetSourceAsync(ms);

        // create a writable bitmap of the right size
        WriteableBitmap wb = new WriteableBitmap(bm.PixelWidth, bm.PixelHeight);
        ms.Seek(0);

        // load the writable bitpamp from the stream
        await wb.SetSourceAsync(ms);

               GeneralTransform transform = Photo.TransformToVisual(LayoutRoot);
        Point controlPosition = transform.TransformPoint(new Point(0, 0));
        int pointX = (int)controlPosition.X;
        int pointY = (int)controlPosition.Y;

        int CropPosX = 0 - pointX;
        int CropPosY = 0 - pointY;

        int UIXPos = (int)Math.Round(CropPosX * compositeTranslation.ScaleX);
        int UIYPos = 413 + (int)Math.Round(CropPosY * compositeTranslation.ScaleY);

        double ImgFactor = ImgWidth / Photo.ActualWidth;
        int ImgXPos = (int)Math.Round(UIXPos * ImgFactor);
        int ImgYPos = (int)Math.Round(UIYPos * ImgFactor);

        //int CropWidth = 864;
        //int CropHeight = 605;



        int CropWidth = (int)Math.Round(864 * ImgFactor);
        int CropHeight = (int)Math.Round(605 * ImgFactor);
        WriteableBitmap wb2 = wb.Crop(ImgXPos, ImgYPos, CropWidth, CropHeight);
        CroppedImage.Source = wb2;
    }

任何指针都非常感谢!

Lumia Imaging SDK(项目:Image Sequencer)正是我需要的东西,但他们的示例基于 Silverlight。WinRT 不再支持视口之类的东西:

http://developer.nokia.com/resources/library/Lumia/nokia-imaging-sdk/sample-projects/image-sequencer.html#toc_Seealso

PS 微软真的应该停止在他们的平台上乱搞。过去曾经有效的东西不再适用,没有其他好的选择。超级沮丧。

4

0 回答 0