我正在开发一个 UWP 应用程序,它有一个带有子元素、Image 和 TextBlock 的网格。我有两件事想要实现并且需要帮助。
如何使用预定义名称将 Grid 元素及其子内容作为图像(最好是 PNG)保存在本地文件夹中?
如何取回保存的图片,然后将其作为附件与其他兼容应用共享?
例子:
<StackPanel Orientation="Vertical">
<Grid Name="myGrid"
HorizontalAlignment="Stretch"
Background="Black">
<Image Name="myImage"
Source="Assets/image1.png"
Stretch="Uniform"/>
<TextBlock Name="myTextBlock"
HorizontalAlignment="Center"
VerticalAlignment="Center"
TextWrapping="Wrap"
Text="Sample user text"/>
</Grid>
<Button Name="saveButton"
Content="Save"
Margin="10,10,0,0"
Click="saveButton_Click" />
<Button Name="shareButton"
Content="Share"
Margin="10,10,0,0"
Click="shareButton_Click" />
</StackPanel>
编辑:在 saveButton_Click 事件中尝试了这段代码。似乎不起作用。
RenderTargetBitmap rtb = new RenderTargetBitmap();
await rtb.RenderAsync(myGrid);
var pixelBuffer = await rtb.GetPixelsAsync();
var pixels = pixelBuffer.ToArray();
var displayInformation = DisplayInformation.GetForCurrentView();
var stream = new InMemoryRandomAccessStream();
var encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.PngEncoderId, stream);
encoder.SetPixelData(BitmapPixelFormat.Bgra8,
BitmapAlphaMode.Premultiplied,
(uint)rtb.PixelWidth,
(uint)rtb.PixelHeight,
displayInformation.RawDpiX,
displayInformation.RawDpiY,
pixels);
await encoder.FlushAsync();
stream.Seek(0);
FileStream filestream = File.Create("C:\\Users\\pcUser\\Desktop\\testimage.png", (int)stream.Size);
EDIT2:尝试了这段代码。它似乎有点工作,但我只得到一个黑色图像,这可能是因为它只保存 myGrid,而不是 child 内容。
RenderTargetBitmap rtb = new RenderTargetBitmap();
await rtb.RenderAsync(quoteGrid);
var pixelBuffer = await rtb.GetPixelsAsync();
var pixels = pixelBuffer.ToArray();
var displayInformation = DisplayInformation.GetForCurrentView();
var stream = new InMemoryRandomAccessStream();
var encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.PngEncoderId, stream);
encoder.SetPixelData(BitmapPixelFormat.Bgra8,
BitmapAlphaMode.Premultiplied,
(uint)rtb.PixelWidth,
(uint)rtb.PixelHeight,
displayInformation.RawDpiX,
displayInformation.RawDpiY,
pixels);
await encoder.FlushAsync();
stream.Seek(0);
var wbm = new WriteableBitmap(rtb.PixelWidth, rtb.PixelHeight);
await wbm.SetSourceAsync(stream);
StorageFolder folder = ApplicationData.Current.LocalFolder;
if (folder != null)
{
StorageFile file = await folder.CreateFileAsync("testImage" + ".png", CreationCollisionOption.ReplaceExisting);
using (var storageStream = await file.OpenAsync(FileAccessMode.ReadWrite))
{
encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.PngEncoderId, storageStream);
var pixelStream = wbm.PixelBuffer.AsStream();
await pixelStream.ReadAsync(pixels, 0, pixels.Length);
encoder.SetPixelData(BitmapPixelFormat.Bgra8, BitmapAlphaMode.Premultiplied, (uint)wbm.PixelWidth, (uint)wbm.PixelHeight, displayInformation.RawDpiX, displayInformation.RawDpiY, new byte[pixelStream.Length]);
await encoder.FlushAsync();
}
}
最佳答案
How do I save the Grid element along with it's child contents as an image(preferably PNG) in the local folder with a predefined name?
我已经检查了你的代码。您不需要使用 WriteableBitmap
,只需将文件流传递给 BitmapEncoder.CreateAsync
方法即可。详情请查看以下代码:
private async void saveButton_Click(object sender, RoutedEventArgs e)
{
RenderTargetBitmap rtb = new RenderTargetBitmap();
await rtb.RenderAsync(myGrid);
var pixelBuffer = await rtb.GetPixelsAsync();
var pixels = pixelBuffer.ToArray();
var displayInformation = DisplayInformation.GetForCurrentView();
var file = await ApplicationData.Current.LocalFolder.CreateFileAsync("testImage" + ".png", CreationCollisionOption.ReplaceExisting);
using (var stream = await file.OpenAsync(FileAccessMode.ReadWrite))
{
var encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.PngEncoderId, stream);
encoder.SetPixelData(BitmapPixelFormat.Bgra8,
BitmapAlphaMode.Premultiplied,
(uint)rtb.PixelWidth,
(uint)rtb.PixelHeight,
displayInformation.RawDpiX,
displayInformation.RawDpiY,
pixels);
await encoder.FlushAsync();
}
}
How do I retrieve this saved image back and then include it as an attachment to share with other compatible apps?
对于您的情况,您将图片保存在本地文件夹中。所以如果你想得到它,你需要使用存储 API。例如:
var file = await ApplicationData.Current.LocalFolder.GetFileAsync("testImage.png");
关于“将其作为附件分享给其他兼容应用”,可以引用官方Sharing content source app sample了解详情。
关于c# - (UWP) 将网格另存为 png,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41354024/