Skip to content

Commit

Permalink
fix deadlock with dx screen capture
Browse files Browse the repository at this point in the history
  • Loading branch information
Aytackydln committed Jun 15, 2024
1 parent 0c141dd commit 526d6d9
Show file tree
Hide file tree
Showing 2 changed files with 19 additions and 40 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -3,29 +3,36 @@
using System.Drawing;
using System.Linq;
using System.Threading;
using System.Threading.Tasks;
using System.Windows;
using SharpDX.DXGI;
using SharpDX.Mathematics.Interop;

namespace AuroraRgb.Settings.Layers.Ambilight;

internal sealed class DxScreenCapture : IScreenCapture, IAsyncDisposable
internal sealed class DxScreenCapture : IScreenCapture
{
public event EventHandler<Bitmap>? ScreenshotTaken;

private static readonly Dictionary<Output5, DesktopDuplicator> Duplicators = new();

private static readonly SemaphoreSlim Semaphore = new(1, 1);
private static readonly object Lock = new();

private Rectangle _currentBounds = Rectangle.Empty;
private DesktopDuplicator? _desktopDuplicator;

public void Capture(Rectangle desktopRegion, Bitmap bitmap)
{
SetTarget(desktopRegion);

lock (Lock)
{
CaptureLocked(bitmap);
}
}

private void CaptureLocked(Bitmap bitmap)
{
try
{
Semaphore.Wait();
if (_currentBounds.IsEmpty)
return;

Expand All @@ -36,6 +43,7 @@ public void Capture(Rectangle desktopRegion, Bitmap bitmap)
{
_desktopDuplicator = null;
}

return;
}
ScreenshotTaken?.Invoke(this, capture);
Expand All @@ -49,8 +57,6 @@ public void Capture(Rectangle desktopRegion, Bitmap bitmap)
_desktopDuplicator = null;
}
Thread.Sleep(2000);
} finally {
Semaphore.Release();
}
}

Expand Down Expand Up @@ -81,18 +87,13 @@ private void SetTarget(Rectangle captureRegion)

_currentBounds = screenWindowRectangle;

try

lock (Lock)
{
Semaphore.Wait();

if (Duplicators.TryGetValue(currentOutput, out _desktopDuplicator)) return;
_desktopDuplicator = new DesktopDuplicator(currentOutput);
Duplicators.Add(currentOutput, _desktopDuplicator);
}
finally
{
Semaphore.Release();
}
}

public IEnumerable<string> GetDisplays() => GetOutputs().Select((s, index) =>
Expand Down Expand Up @@ -124,16 +125,11 @@ private static List<Output5> GetOutputs()

private static void FactoryDisposed(object? sender, EventArgs e)
{
try
lock (Lock)
{
Semaphore.Wait();
_outputs = null;
Duplicators.Clear();
}
finally
{
Semaphore.Release();
}
}

private static void OutputDisposed(object? sender, EventArgs e)
Expand All @@ -156,27 +152,9 @@ private static bool RectangleContains(RawRectangle containingRectangle, Rectangl

public void Dispose()
{
try
{
Semaphore.Wait();
_desktopDuplicator = null;
}
finally
{
Semaphore.Release();
}
}

public async ValueTask DisposeAsync()
{
try
lock (Lock)
{
await Semaphore.WaitAsync();
_desktopDuplicator = null;
}
finally
{
Semaphore.Release();
}
}
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
// Based on https://github.com/sharpdx/SharpDX-Samples/blob/master/Desktop/Direct3D11.1/ScreenCapture/Program.cs

using System;
using System.Diagnostics;
using System.Drawing;
using System.Drawing.Imaging;
using System.Windows;
Expand Down Expand Up @@ -33,7 +34,7 @@ public DesktopDuplicator(Output5 output)
Dispose();
});
var deviceFlags = DeviceCreationFlags.SingleThreaded;
if (Global.isDebug)
if (Global.isDebug && Debugger.IsAttached)
{
deviceFlags |= DeviceCreationFlags.Debug;
}
Expand Down

0 comments on commit 526d6d9

Please sign in to comment.