private SizeInt32 _lastSize;
private GraphicsCaptureItem _item;
private Direct3D11CaptureFramePool _framePool;
private GraphicsCaptureSession _session;
// Non-API related members.
private CanvasDevice _canvasDevice;
private CompositionGraphicsDevice _compositionGraphicsDevice;
private Compositor _compositor;
private CompositionDrawingSurface _surface;
private CanvasBitmap _currentFrame;
private string _screenshotFilename = "test.png";
private AppWindow m_AppWindow;
public MainWindow()
{
this.InitializeComponent();
m_AppWindow = GetAppWindowForCurrentWindow();
m_AppWindow.Title = "Test";
m_AppWindow.SetIcon("C:\\Users\\name\\OneDrive\\Pictures\\zup.0849b3176cec0e8f7fe3.ico");
var titleBar = m_AppWindow.TitleBar;
titleBar.BackgroundColor = Colors.Purple;
titleBar.ForegroundColor = Colors.Purple;
titleBar.InactiveBackgroundColor = Colors.Purple;
titleBar.InactiveForegroundColor = Colors.Purple;
titleBar.ButtonForegroundColor = Colors.Orange;
titleBar.ButtonBackgroundColor = Colors.Purple;
titleBar.ButtonInactiveForegroundColor = Colors.Orange;
titleBar.ButtonInactiveBackgroundColor = Colors.Purple;
}
private AppWindow GetAppWindowForCurrentWindow()
{
IntPtr hWnd = WindowNative.GetWindowHandle(this);
WindowId wndId = Win32Interop.GetWindowIdFromWindow(hWnd);
return AppWindow.GetFromWindowId(wndId);
}
private async void myButton_Click(object sender, RoutedEventArgs e)
{
await StartCaptureAsync();
}
public async Task StartCaptureAsync()
{
// The GraphicsCapturePicker follows the same pattern the
// file pickers do.
var hWnd = await Task.Run(() => WinRT.Interop.WindowNative.GetWindowHandle(this));
var picker = new GraphicsCapturePicker();
InitializeWithWindow.Initialize(picker, hWnd);
GraphicsCaptureItem item = await picker.PickSingleItemAsync();
// The item may be null if the user dismissed the
// control without making a selection or hit Cancel.
if (item != null)
{
Debug.WriteLine(item.DisplayName);
StartCaptureInternal(item);
}
}
private void Stop(object sender, RoutedEventArgs e)
{
StopCapture();
}
public void StartCaptureInternal(GraphicsCaptureItem item)
{
_canvasDevice = new CanvasDevice();
_item = item;
_lastSize = _item.Size;
int i = 1;
_framePool = Direct3D11CaptureFramePool.Create(
_canvasDevice, // D3D device
Windows.Graphics.DirectX.DirectXPixelFormat.B8G8R8A8UIntNormalized, // Pixel format
60, // Number of frames
_item.Size); // Size of the buffers
Debug.WriteLine(i);
_framePool.FrameArrived += (s, a) =>
{
// The FrameArrived event is raised for every frame on the thread
// that created the Direct3D11CaptureFramePool. This means we
// don't have to do a null-check here, as we know we're the only
// one dequeueing frames in our application.
// NOTE: Disposing the frame retires it and returns
// the buffer to the pool.
using (var frame = _framePool.TryGetNextFrame())
{
ProcessFrame(frame);
i++;
Debug.WriteLine(i);
Debug.WriteLine(frame.GetType().Name);
}
};
_item.Closed += (s, a) =>
{
StopCapture();
};
_session = _framePool.CreateCaptureSession(_item);
_session.StartCapture();
}
public void StopCapture()
{
_session?.Dispose();
_framePool?.Dispose();
_item = null;
_session = null;
_framePool = null;
}
private void ProcessFrame(Direct3D11CaptureFrame frame)
{
// Resize and device-lost leverage the same function on the
// Direct3D11CaptureFramePool. Refactoring it this way avoids
// throwing in the catch block below (device creation could always
// fail) along with ensuring that resize completes successfully and
// isn’t vulnerable to device-lost.
bool needsReset = false;
bool recreateDevice = false;
if ((frame.ContentSize.Width != _lastSize.Width) ||
(frame.ContentSize.Height != _lastSize.Height))
{
needsReset = true;
_lastSize = frame.ContentSize;
}
try
{
// Take the D3D11 surface and draw it into a
// Composition surface.
// Convert our D3D11 surface into a Win2D object.
CanvasBitmap canvasBitmap = CanvasBitmap.CreateFromDirect3D11Surface(
_canvasDevice,
frame.Surface);
_currentFrame = canvasBitmap;
// Helper that handles the drawing for us.
//FillSurfaceWithBitmap(canvasBitmap);
}
// This is the device-lost convention for Win2D.
catch (Exception e) when (_canvasDevice.IsDeviceLost(e.HResult))
{
// We lost our graphics device. Recreate it and reset
// our Direct3D11CaptureFramePool.
needsReset = true;
recreateDevice = true;
}
if (needsReset)
{
ResetFramePool(frame.ContentSize, recreateDevice);
}
}
private void ResetFramePool(SizeInt32 size, bool recreateDevice)
{
do
{
try
{
if (recreateDevice)
{
_canvasDevice = new CanvasDevice();
}
_framePool.Recreate(
_canvasDevice,
Windows.Graphics.DirectX.DirectXPixelFormat.B8G8R8A8UIntNormalized,
2,
size);
}
// This is the device-lost convention for Win2D.
catch (Exception e) when (_canvasDevice.IsDeviceLost(e.HResult))
{
_canvasDevice = null;
recreateDevice = true;
}
} while (_canvasDevice == null);
}`