最近、私は UWP を学習し、簡単なデモを作成しようとしていましたが、Aero のような簡単なライブ ブラー効果を生成したいだけです。時々便利です(リアルタイムカメラフィルターなど)ので、次のようなアイデアを作りました:
まず、win2D ライブラリをインポートし、RootGrid に CanvasAnimatedControl を配置しました。
<canvas:CanvasAnimatedControl x:Name="BlurLayer" Draw="BlurLayer_Draw"
VerticalAlignment="Stretch" HorizontalAlignment="Stretch"/>
このぼかしレイヤーのリソースはFrameです:
<Frame x:Name="MainFrame" LayoutUpdated="MainFrame_LayoutUpdated"
VerticalAlignment="Stretch" HorizontalAlignment="Stretch"/>
フレームが更新されるたびに、MainFrame_LayoutUpdatedメソッドは RenderTargetBitmap を使用してショートカットを保存しようとしますが、win2D はこのオブジェクトを CanvasBitmap として受け取ることができないため、byte[] に変換されて保存されます。
RenderTargetBitmap renderer = new RenderTargetBitmap();
CanvasBitmap bitmap;
byte[] RendererStream;
public static int FrameWidth;
public static int FrameHeight;
public ICanvasImage RenderFinal;
public bool Frame_Updated = false;
private async void MainFrame_LayoutUpdated(object sender, object e)
{
await renderer.RenderAsync(MainFrame);
FrameWidth = renderer.PixelWidth;
FrameHeight = renderer.PixelHeight;
RendererStream = WindowsRuntimeBufferExtensions.ToArray(await renderer.GetPixelsAsync());
if (FrameHeight != 0)
Frame_Updated = true;
}
BlurLayer_Drawメソッドでは、更新してぼかし効果を適用するだけです: private void BlurLayer_Draw(ICanvasAnimatedControl sender,
CanvasAnimatedDrawEventArgs args)
{
if (Frame_Updated)
{
bitmap = CanvasBitmap.CreateFromBytes(sender, RendererStream, FrameWidth, FrameHeight, DirectXPixelFormat.B8G8R8A8UIntNormalized);
RenderFinal = new GaussianBlurEffect
{
Source = bitmap
};
RenderFinal.BorderMode = EffectBorderMode.Hard;
RenderFinal.BlurAmount = 8.0f;
Frame_Updated = false;
}
if (RenderFinal != null)
args.DrawingSession.DrawImage(RenderFinal);
}
これがすべて完了すると、うまくいきました。しかし、このソリューションは本当にひどかったです。win2D Canvas は深刻な遅れをとっていました。では、高性能にするためにはどうすればよいのでしょうか。