UWP:如何将图像附加到InkCanvas?
我必须用相机拍摄一张照片,或者将它从文件中加载到画布中,在保存到文件夹后,画布应该进行编辑以突出显示上面的某些内容 至于现在,我用的是:UWP:如何将图像附加到InkCanvas?,uwp,windows-10,code-behind,inkcanvas,Uwp,Windows 10,Code Behind,Inkcanvas,我必须用相机拍摄一张照片,或者将它从文件中加载到画布中,在保存到文件夹后,画布应该进行编辑以突出显示上面的某些内容 至于现在,我用的是: <Grid x:Name="grid"> <Image Source="/Assets/stainless-images-110606.jpg" x:Name="ImageToEdit" Stretch="Uniform" /> <StackPanel Background="LightGreen" Width="
<Grid x:Name="grid">
<Image Source="/Assets/stainless-images-110606.jpg" x:Name="ImageToEdit" Stretch="Uniform" />
<StackPanel Background="LightGreen" Width="700" Height="700" x:Name="StackPanel">
<InkCanvas x:Name="MyInkCanvas" Width="{Binding Width, ElementName=StackPanel}" Height="{Binding Height, ElementName=StackPanel}"/>
</StackPanel>
<InkToolbar TargetInkCanvas="{x:Bind MyInkCanvas}" Name="inkToolbar"/>
<Button Content="Save" Click="Button_Click" HorizontalAlignment="Right"/>
</Grid>
这就是我如何从xaml获得全部内容的原因:
public static async Task<IRandomAccessStream> RenderToRandomAccessStream(this UIElement element)
{
RenderTargetBitmap rtb = new RenderTargetBitmap();
await rtb.RenderAsync(element);
var pixelBuffer = await rtb.GetPixelsAsync();
var pixels = pixelBuffer.ToArray();
// Useful for rendering in the correct DPI
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);
return stream;
}
公共静态异步任务RenderToRandomAccessStream(此UIElement)
{
RenderTargetBitmap rtb=新建RenderTargetBitmap();
等待rtb.RenderAsync(元素);
var pixelBuffer=await rtb.GetPixelsAsync();
var pixels=pixelBuffer.ToArray();
//用于以正确的DPI进行渲染
var displayInformation=displayInformation.GetForCurrentView();
var stream=新的InMemoryRandomAccessStream();
var encoder=await BitmapEncoder.CreateAsync(BitmapEncoder.PngEncoderId,stream);
编码器.SetPixelData(BitmapPixelFormat.Bgra8,
BitmapAlphaMode.预乘,
(uint)rtb.PixelWidth,
(uint)rtb像素高度,
displayInformation.RawDpiX,
displayInformation.RawDpiY,
像素);
等待编码器。FlushAsync();
stream.Seek(0);
回流;
}
当我从相机中捕获照片时,我将图像源设置为photo,但当保存整个内容时,它只保存照片,而不保存画布上的笔划。我的假设是,我必须以某种方式将从摄影机获得的流附加到inkCanvas。根据类的“XAML视觉效果和渲染目标位图捕获功能”:
无法捕获的内容将在捕获的图像中显示为空白,但同一视觉树中的其他内容仍可以捕获并呈现(无法捕获的内容的存在不会使该XAML合成的整个捕获无效)
因此,InkCanvas
的内容可能无法捕获。似乎没有API可以直接捕获同时附加图像的InkCanvas
。但是你可以用。更多详情请参考
您可以使用方法结合该方法在画布设备
上绘制它们,然后可以将照片和笔划一起保存。例如:
<StackPanel Padding="30" Background="{ThemeResource ApplicationPageBackgroundThemeBrush}">
<Grid>
<Image
x:Name="imgbackground"
Source="/Assets/ob_0_0.png"
Stretch="None" />
<InkCanvas x:Name="ink" />
</Grid>
<StackPanel Orientation="Horizontal">
<Button
x:Name="btnUpdate"
Margin="10"
Click="btnUpdate_Click"
Content="update ink size, click me firstly" />
<Button
Margin="10"
Click="BtnSave_Click"
Content="Save" />
</StackPanel>
</StackPanel>
BitmapImage inkimage;
public MainPage()
{
this.InitializeComponent();
ink.InkPresenter.InputDeviceTypes = Windows.UI.Core.CoreInputDeviceTypes.Mouse | CoreInputDeviceTypes.Touch;
var attr = new InkDrawingAttributes();
attr.Color = Colors.Red;
attr.IgnorePressure = true;
attr.PenTip = PenTipShape.Circle;
attr.Size = new Size(4, 10);
ink.InkPresenter.UpdateDefaultDrawingAttributes(attr);
}
private async void BtnSave_Click(object sender, RoutedEventArgs e)
{
StorageFile inputFile = await StorageFile.GetFileFromApplicationUriAsync(inkimage.UriSource);
CanvasDevice device = CanvasDevice.GetSharedDevice();
CanvasRenderTarget renderTarget = new CanvasRenderTarget(device, (int)ink.ActualWidth, (int)ink.ActualHeight, 96);
using (var ds = renderTarget.CreateDrawingSession())
{
ds.Clear(Colors.White);
var image = await CanvasBitmap.LoadAsync(device, inputFile.Path, 96);
ds.DrawImage(image);// Draw image firstly
ds.DrawInk(ink.InkPresenter.StrokeContainer.GetStrokes());// Draw the stokes
}
//Save them to the output.jpg in picture folder
StorageFolder storageFolder = KnownFolders.SavedPictures;
var file = await storageFolder.CreateFileAsync("output.jpg", CreationCollisionOption.ReplaceExisting);
using (var fileStream = await file.OpenAsync(FileAccessMode.ReadWrite))
{
await renderTarget.SaveAsync(fileStream, CanvasBitmapFileFormat.Jpeg, 1f);
}
}
private void btnUpdate_Click(object sender, RoutedEventArgs e)
{
//Get the image source that for attaching to the inkcanvas, update the inkcanvas to be same size with image.
inkimage = (BitmapImage)imgbackground.Source;
var imagewidth = inkimage.PixelWidth;
var imageheight = inkimage.PixelWidth;
ink.Height = imageheight;
ink.Width = imagewidth;
ink.UpdateLayout();
}