Browse Source

[MONOMAC] Pass frames back to UI thread instead of using lockFocusIfCanDraw

pull/1240/head
Nikita Tsukanov 9 years ago
parent
commit
a0c4ec9039
  1. 29
      src/OSX/Avalonia.MonoMac/EmulatedFramebuffer.cs
  2. 30
      src/OSX/Avalonia.MonoMac/TopLevelImpl.cs

29
src/OSX/Avalonia.MonoMac/EmulatedFramebuffer.cs

@ -11,7 +11,7 @@ namespace Avalonia.MonoMac
{
private readonly TopLevelImpl.TopLevelView _view;
private readonly CGSize _logicalSize;
private bool _isDeferred;
private readonly bool _isDeferred;
[DllImport("libc")]
static extern void memset(IntPtr p, int c, IntPtr size);
@ -32,34 +32,12 @@ namespace Avalonia.MonoMac
Address = Marshal.AllocHGlobal(size);
memset(Address, 0, new IntPtr(size));
}
class CocoaDrawLock : IDisposable
{
private readonly NSView _view;
public void Dispose()
{
_view.NonUIUnlockFocus();
}
public CocoaDrawLock(NSView view)
{
_view = view;
}
}
CocoaDrawLock LockCocoaDrawing()
{
if (!_view.NonUILockFocusIfCanDraw())
return null;
return new CocoaDrawLock(_view);
}
public void Dispose()
{
if (Address == IntPtr.Zero)
return;
var nfo = (int) CGBitmapFlags.ByteOrder32Big | (int) CGImageAlphaInfo.PremultipliedLast;
IDisposable drawLock = LockCocoaDrawing();
CGImage image = null;
try
{
@ -69,7 +47,7 @@ namespace Avalonia.MonoMac
image = bContext.ToImage();
lock (_view.SyncRoot)
{
if (!_isDeferred || drawLock != null)
if(!_isDeferred)
{
using (var nscontext = NSGraphicsContext.CurrentContext)
using (var context = nscontext.GraphicsPort)
@ -95,7 +73,6 @@ namespace Avalonia.MonoMac
}
Marshal.FreeHGlobal(Address);
Address = IntPtr.Zero;
drawLock?.Dispose();
}

30
src/OSX/Avalonia.MonoMac/TopLevelImpl.cs

@ -7,7 +7,7 @@ using Avalonia.Controls.Platform.Surfaces;
using Avalonia.Rendering;
using Avalonia.Threading;
using MonoMac.AppKit;
using MonoMac.CoreFoundation;
using MonoMac.CoreGraphics;
using MonoMac.Foundation;
using MonoMac.ObjCRuntime;
@ -37,6 +37,7 @@ namespace Avalonia.MonoMac
private readonly IKeyboardDevice _keyboard;
private NSTrackingArea _area;
private NSCursor _cursor;
private bool _nonUiRedrawQueued;
public CGSize PixelSize { get; set; }
@ -55,7 +56,10 @@ namespace Avalonia.MonoMac
protected override void Dispose(bool disposing)
{
if (disposing)
SetBackBufferImage(null);
{
_backBuffer?.Dispose();
_backBuffer = null;
}
base.Dispose(disposing);
}
@ -69,6 +73,8 @@ namespace Avalonia.MonoMac
public override void DrawRect(CGRect dirtyRect)
{
lock (SyncRoot)
_nonUiRedrawQueued = false;
lock (SyncRoot)
{
if (_backBuffer != null)
@ -93,6 +99,25 @@ namespace Avalonia.MonoMac
{
_backBuffer?.Dispose();
_backBuffer = image;
if (image == null)
return;
if (_nonUiRedrawQueued)
return;
_nonUiRedrawQueued = true;
Dispatcher.UIThread.InvokeAsync(
() =>
{
lock (SyncRoot)
{
if (!_nonUiRedrawQueued)
return;
_nonUiRedrawQueued = false;
}
SetNeedsDisplayInRect(Frame);
Display();
}, DispatcherPriority.Render);
}
}
@ -138,6 +163,7 @@ namespace Avalonia.MonoMac
AddTrackingArea(_area);
UpdateCursor();
_tl?.Resized?.Invoke(_tl.ClientSize);
Dispatcher.UIThread.RunJobs(DispatcherPriority.Layout);
}
InputModifiers GetModifiers(NSEventModifierMask mod)

Loading…
Cancel
Save