Windows应用商店-RenderTargetBitmap创建大小不正确的位图

00

我正在尝试在我的应用拍摄的照片上加水印。我能想到的最简单的方法是使用FrameworkElement来构建图层,然后使用RenderTargetBitmap来创建带有水印的图像。

这是我的XAML的示例。

    <ScrollViewer x:Name="Zoom" Grid.Column="1" HorizontalScrollMode="Enabled" VerticalScrollMode="Enabled" VerticalScrollBarVisibility="Hidden" HorizontalScrollBarVisibility="Hidden" ZoomMode="Enabled">
        <Border x:Name="BgBorder">
            <Grid x:Name="ImageGird" SizeChanged="ImageGird_SizeChanged">
                <Grid x:Name="CaptureGird">
                    <Image x:Name="CapturedImage" Stretch="None" Source="ms-appx:///Assets/Photo.jpg" />
                    <StackPanel x:Name="Watermark" VerticalAlignment="Top" HorizontalAlignment="Left" Background="#6FFFFFFF" Margin="10">
                        <TextBlock Text="Name" Foreground="Black" Margin="10,2.5,10,2.5" />
                        <TextBlock Text="12345" Foreground="Black" Margin="10,2.5,10,2.5"/>
                        <TextBlock Text="54321" Foreground="Black" Margin="10,2.5,10,2.5" />
                    </StackPanel>
                </Grid>
            </Grid>
        </Border>
    </ScrollViewer>

由于他们需要的图像分辨率高,因此将其包裹在A中,ScrollViewer因此可以将其缩小,但是当我尝试使用以下代码创建该图像的位图时,渲染的位图会小于FrameworkElement

private async void Button_Click(object sender, RoutedEventArgs e)
{
    try
    {
        var displayI = DisplayInformation.GetForCurrentView();
        var renderTargetBitmap = new RenderTargetBitmap();
        await renderTargetBitmap.RenderAsync(ImageGird, (int)ImageGird.ActualWidth, (int)ImageGird.ActualHeight);
        IBuffer pixels = await renderTargetBitmap.GetPixelsAsync();
        CapturedImage2.Source = renderTargetBitmap;

        Debug.WriteLine("Button_Click: ImageGrid: " + ImageGird.ActualWidth + "x" + ImageGird.ActualHeight + " RenderTargetBitmap: " + renderTargetBitmap.PixelWidth + "x" + renderTargetBitmap.PixelHeight);
    }
    catch (Exception )
    {
    }
}

调试输出是

Button_Click: ImageGrid: 5344x3008 RenderTargetBitmap: 4096x2306

谁能告诉我为什么渲染的位图比我从中创建它的实际元素小得多?

还有给图像加水印的更好方法吗?

00

感谢@AJBauer向我指出Win2D,我设法非常优雅地解决了这个问题。

    /// <summary>
    /// Create a watermarked image from an image stream
    /// </summary>
    /// <param name="sender">Jpeg image stream.</param>
    private async Task<ImageSource> CreateWaterMarkedImage(IRandomAccessStream stream)
    {
        // Ensure our stream is at the beginning.
        stream.Seek(0);
        // Create our Win2D in memory renderer.
        CanvasDevice device = CanvasDevice.GetSharedDevice();
        CanvasRenderTarget offscreen = new CanvasRenderTarget(device, (float)ImageGird.ActualWidth, (float)ImageGird.ActualHeight, 96);
        // Create our Win2D bitmap
        CanvasBitmap bmp = await CanvasBitmap.LoadAsync(offscreen, stream, 96);
        // Create a text formatter for our watermark
        var format = new CanvasTextFormat()
        {
            FontSize = 40,
            HorizontalAlignment = CanvasHorizontalAlignment.Left,
            VerticalAlignment = CanvasVerticalAlignment.Top,
            WordWrapping = CanvasWordWrapping.Wrap,
            FontFamily = "Arial",
            FontWeight = FontWeights.SemiBold
        };
        // Get a Win2D drawing session instance
        using (CanvasDrawingSession ds = offscreen.CreateDrawingSession())
        {
            // Layer our resulting Watermarked image.
            ds.DrawImage(bmp);
            // Create the Win2D text layout so we can get the bounds.
            var tl = new CanvasTextLayout(ds, "Name\r\n12345\r\n54321", format, 1000, 1000);
            // Create a background for the text
            ds.FillRectangle(10, 10, (float)tl.DrawBounds.Width + 20f, (float)tl.DrawBounds.Height + 20f, new Color() { A = 0x6F, R = 0xFF, G = 0xFF, B = 0xFF });
            // Add the text layout.
            ds.DrawTextLayout(tl, 10, 10, Colors.Black);
            // Clear up the memory.
            tl.Dispose();
        }

        // Create our bitmap so we can return an ImageSource
        BitmapImage im = new BitmapImage();
        using (InMemoryRandomAccessStream oStream = new InMemoryRandomAccessStream())
        {
            // Save the Win2D canvas renderer a stream.
            await offscreen.SaveAsync(oStream, CanvasBitmapFileFormat.Jpeg, 1.0f);
            stream.Seek(0);
            // Stream our Win2D pixels into the Bitmap
            await im.SetSourceAsync(oStream);
            Debug.WriteLine("CreateWaterMarkedImage: ImageGrid: " + ImageGird.ActualWidth + "x" + ImageGird.ActualHeight + " Bitmap: " + im.PixelWidth + "x" + im.PixelHeight);
        }
        // Tidy Up.
        format.Dispose();
        bmp.Dispose();
        offscreen.Dispose();
        device.Dispose();
        return im;
    }

结果调试给了我。

CreateWaterMarkedImage: ImageGrid: 5344x3008 Bitmap: 5344x3008

如果已设置,Image UIElement则显示带水印的图像的来源

CapturedImage2.Source = await CreateWaterMarkedImage(photoStream);

此示例非常适合我的需求,但是,如果您使用Win2D XAML控件,那么任何人都应该可以轻松对其进行调整。

本文收集自互联网,转载请注明来源。

如有侵权,请联系[email protected] 删除。

编辑于
0

我来说两句

0条评论
登录后参与评论

相关文章

来自分类Dev

创建Windows应用商店应用程序

来自分类Dev

使用 Visual Studio 创建 Windows 8.1 商店应用程序

来自分类Dev

应用商店,大小限制等

来自分类Dev

从命令提示符创建Windows应用商店应用程序包

来自分类Dev

如何在Windows应用商店应用中创建键盘快捷键(如Ctrl + C)

来自分类Dev

从命令提示符创建Windows应用商店应用程序包

来自分类Dev

Windows应用商店开发

来自分类Dev

Windows应用商店更新

来自分类Dev

Windows应用商店的应用要求

来自分类Dev

VOCBboxDataset 应用于我的数据集时返回不正确的数据集大小

来自分类Dev

当我更新现有的Windows应用商店应用程序时,它会增加到该应用程序的先前大小吗?

来自分类Dev

样式应用不正确

来自分类Dev

闹钟应用不正确

来自分类Dev

CSS应用不正确?

来自分类Dev

样式应用不正确

来自分类Dev

Windows应用商店中的GetInterfaces

来自分类Dev

Windows应用商店中的GetInterfaces

来自分类Dev

Windows应用商店-像素阵列

来自分类Dev

Windows应用商店的主题资源

来自分类Dev

Windows应用商店的无敌错误

来自分类Dev

我的Windows服务安装不正确?

来自分类Dev

Windows MediaPack安装不正确

来自分类Dev

Windows 显示日期格式不正确

来自分类Dev

Tableviewcell 有自定义视图,应用程序运行时大小不正确(下图)

来自分类Dev

如何在Xcode中检查应用的近似应用商店大小

来自分类Dev

Windows应用商店应用-显示PDF

来自分类Dev

Windows应用商店应用部署位置

来自分类Dev

Windows 10中Qt Desktop应用程序的不正确缩放

来自分类Dev

从UIView创建的IMessage MSSticker视图大小不正确