mirror of
https://github.com/Ryujinx/GLWidget.git
synced 2024-12-22 13:55:31 +00:00
glxcontexts
This commit is contained in:
parent
6fed327bc6
commit
e59894411d
|
@ -55,11 +55,13 @@ namespace OpenTK
|
|||
|
||||
public bool HandleRendering { get; set; } = false;
|
||||
|
||||
#endregion
|
||||
public IGraphicsContext NativeGraphicsContext { get; private set; }
|
||||
|
||||
#region Attributes
|
||||
#endregion
|
||||
|
||||
private bool _initialized;
|
||||
#region Attributes
|
||||
|
||||
private bool _initialized;
|
||||
|
||||
#endregion
|
||||
|
||||
|
@ -184,13 +186,13 @@ namespace OpenTK
|
|||
OnRenderFrame();
|
||||
}
|
||||
|
||||
cr.SetSourceColor(new Color(0, 0, 0, 1));
|
||||
/*cr.SetSourceColor(new Color(0, 0, 0, 1));
|
||||
cr.Paint();
|
||||
|
||||
var scale = this.ScaleFactor;
|
||||
|
||||
Gdk.CairoHelper.DrawFromGl(cr, this.Window, _renderbuffer, (int)ObjectLabelIdentifier.Renderbuffer, scale, 0, 0, AllocatedWidth, AllocatedHeight);
|
||||
|
||||
*/
|
||||
return true;
|
||||
}
|
||||
|
||||
|
@ -198,11 +200,13 @@ namespace OpenTK
|
|||
{
|
||||
GL.Flush();
|
||||
|
||||
QueueDraw();
|
||||
//QueueDraw();
|
||||
|
||||
RecreateFramebuffer();
|
||||
OpenTK.GraphicsContext.GetCurrentContext(Window.Handle).SwapBuffers();
|
||||
|
||||
if (HandleRendering)
|
||||
//RecreateFramebuffer();
|
||||
|
||||
if (!HandleRendering)
|
||||
{
|
||||
ClearCurrent();
|
||||
}
|
||||
|
@ -210,8 +214,9 @@ namespace OpenTK
|
|||
|
||||
public void MakeCurrent()
|
||||
{
|
||||
GraphicsContext?.MakeCurrent();
|
||||
GL.BindFramebuffer(FramebufferTarget.Framebuffer, _framebuffer);
|
||||
ClearCurrent();
|
||||
NativeGraphicsContext?.MakeCurrent();
|
||||
GL.BindFramebuffer(FramebufferTarget.Framebuffer, 0);
|
||||
}
|
||||
|
||||
public void ClearCurrent()
|
||||
|
@ -292,12 +297,16 @@ namespace OpenTK
|
|||
|
||||
GraphicsContext.MakeCurrent();
|
||||
|
||||
if (!GTKBindingContext.Loaded)
|
||||
if (!GTKBindingHelper.Loaded)
|
||||
{
|
||||
GTKBindingContext.InitializeGlBindings();
|
||||
GTKBindingHelper.InitializeGlBindings();
|
||||
}
|
||||
|
||||
CreateFramebuffer();
|
||||
OpenTK.GraphicsContext.Display = this.Display.Handle;
|
||||
|
||||
NativeGraphicsContext = OpenTK.GraphicsContext.GetCurrentContext(this.Window.Handle);
|
||||
|
||||
// CreateFramebuffer();
|
||||
|
||||
OnInitialized();
|
||||
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
using System;
|
||||
using System;
|
||||
using OpenTK;
|
||||
using System.Runtime.InteropServices;
|
||||
using System.Collections.Generic;
|
||||
|
@ -6,8 +6,29 @@ using System.Reflection;
|
|||
|
||||
namespace OpenTK
|
||||
{
|
||||
public class GTKBindingContext : IBindingsContext
|
||||
public class GTKBindingHelper : IBindingsContext
|
||||
{
|
||||
public static OSPlatform CurrentPlatform
|
||||
{
|
||||
get
|
||||
{
|
||||
if (RuntimeInformation.IsOSPlatform(OSPlatform.Windows))
|
||||
{
|
||||
return OSPlatform.Windows;
|
||||
}
|
||||
else if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux))
|
||||
{
|
||||
return OSPlatform.Linux;
|
||||
}
|
||||
else if (RuntimeInformation.IsOSPlatform(OSPlatform.OSX))
|
||||
{
|
||||
return OSPlatform.OSX;
|
||||
}
|
||||
|
||||
return OSPlatform.Create("None");
|
||||
}
|
||||
}
|
||||
|
||||
public static bool Loaded;
|
||||
|
||||
private const string GlxLibrary = "libGL.so.1";
|
||||
|
@ -24,7 +45,7 @@ namespace OpenTK
|
|||
|
||||
public IntPtr GetProcAddress(string procName)
|
||||
{
|
||||
if (RuntimeInformation.IsOSPlatform(OSPlatform.Windows))
|
||||
if (CurrentPlatform == OSPlatform.Windows)
|
||||
{
|
||||
var addr = GetProcAddressWgl(procName);
|
||||
if (addr == null || addr == IntPtr.Zero)
|
||||
|
@ -40,11 +61,11 @@ namespace OpenTK
|
|||
}
|
||||
return addr;
|
||||
}
|
||||
else if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux))
|
||||
else if (CurrentPlatform == OSPlatform.Linux)
|
||||
{
|
||||
return GetProcAddressGlx(procName);
|
||||
}
|
||||
else if(RuntimeInformation.IsOSPlatform(OSPlatform.OSX))
|
||||
else if(CurrentPlatform == OSPlatform.OSX)
|
||||
{
|
||||
var osxAddr = !IsGlxRequired ? GetProcAddressOSX(procName) : GetProcAddressGlx(procName);
|
||||
if (osxAddr != IntPtr.Zero)
|
||||
|
@ -78,7 +99,7 @@ namespace OpenTK
|
|||
return;
|
||||
}
|
||||
|
||||
var provider = new GTKBindingContext();
|
||||
var provider = new GTKBindingHelper();
|
||||
|
||||
void LoadBindings(string typeNamespace)
|
||||
{
|
||||
|
@ -165,7 +186,7 @@ namespace OpenTK
|
|||
return symbol;
|
||||
}
|
||||
|
||||
private static class UnsafeNativeMethods
|
||||
internal static class UnsafeNativeMethods
|
||||
{
|
||||
[DllImport("kernel32.dll", SetLastError = true)]
|
||||
internal static extern IntPtr GetProcAddress(IntPtr handle, string funcname);
|
||||
|
@ -179,6 +200,18 @@ namespace OpenTK
|
|||
[DllImport(WglLibrary, EntryPoint = "wglGetProcAddress", ExactSpelling = true, SetLastError = true)]
|
||||
public static extern IntPtr wglGetProcAddress(string lpszProc);
|
||||
|
||||
[DllImport(WglLibrary, EntryPoint = "wglGetCurrentContext")]
|
||||
public extern static IntPtr wglGetCurrentContext();
|
||||
|
||||
[DllImport(WglLibrary, EntryPoint = "wglGetCurrentDC")]
|
||||
public static extern IntPtr wglGetCurrentDC();
|
||||
|
||||
[DllImport(WglLibrary, EntryPoint = "wglSwapBuffers", ExactSpelling = true)]
|
||||
public static extern bool wglSwapBuffers(IntPtr hdc);
|
||||
|
||||
[DllImport("opengl32.dll", SetLastError = true, EntryPoint = "wglMakeCurrent")]
|
||||
public static extern bool WglMakeCurrent(IntPtr hdc, IntPtr hglrc);
|
||||
|
||||
[DllImport(OSXLibrary, EntryPoint = "NSIsSymbolNameDefined")]
|
||||
public static extern bool NSIsSymbolNameDefined(string s);
|
||||
|
||||
|
@ -188,6 +221,15 @@ namespace OpenTK
|
|||
[DllImport(OSXLibrary, EntryPoint = "NSAddressOfSymbol")]
|
||||
public static extern IntPtr NSAddressOfSymbol(IntPtr symbol);
|
||||
|
||||
[DllImport(GlxLibrary, EntryPoint = "glXGetCurrentContext")]
|
||||
public static extern IntPtr glXGetCurrentContext();
|
||||
|
||||
[DllImport(GlxLibrary, EntryPoint = "glXMakeCurrent")]
|
||||
public static extern bool glXMakeCurrent(IntPtr display, IntPtr drawable, IntPtr context);
|
||||
|
||||
[DllImport(GlxLibrary, EntryPoint = "glXSwapBuffers")]
|
||||
public static extern void glXSwapBuffers(IntPtr display, IntPtr drawable);
|
||||
|
||||
public const int RTLD_LAZY = 1;
|
||||
|
||||
public const int RTLD_NOW = 2;
|
||||
|
@ -200,6 +242,26 @@ namespace OpenTK
|
|||
|
||||
[DllImport("dl")]
|
||||
public static extern string dlerror();
|
||||
|
||||
public const string GdkNativeDll = "libgdk-3-0.dll";
|
||||
|
||||
[DllImport(GdkNativeDll, CallingConvention = CallingConvention.Cdecl)]
|
||||
public static extern IntPtr gdk_win32_drawable_get_handle(IntPtr raw);
|
||||
|
||||
[DllImport(GdkNativeDll, CallingConvention = CallingConvention.Cdecl)]
|
||||
public static extern IntPtr gdk_win32_hdc_get(IntPtr drawable, IntPtr gc, int usage);
|
||||
|
||||
[DllImport(GdkNativeDll, CallingConvention = CallingConvention.Cdecl)]
|
||||
public static extern void gdk_win32_hdc_release(IntPtr drawable, IntPtr gc, int usage);
|
||||
|
||||
[DllImport("libgdk-3.so.0", CallingConvention = CallingConvention.Cdecl)]
|
||||
public static extern IntPtr gdk_x11_display_get_xdisplay(IntPtr raw);
|
||||
|
||||
[DllImport("libgdk-3.so.0", CallingConvention = CallingConvention.Cdecl)]
|
||||
public static extern IntPtr gdk_x11_window_get_xid(IntPtr raw);
|
||||
|
||||
[DllImport(GdkNativeDll, CallingConvention = CallingConvention.Cdecl)]
|
||||
public static extern void gdk_window_get_internal_paint_info(IntPtr raw, out IntPtr real_drawable, out int x, out int y);
|
||||
}
|
||||
|
||||
private static class Delegates
|
120
GLWidget/GraphicsContext.cs
Normal file
120
GLWidget/GraphicsContext.cs
Normal file
|
@ -0,0 +1,120 @@
|
|||
using System;
|
||||
using System.Runtime.InteropServices;
|
||||
using static OpenTK.GTKBindingHelper;
|
||||
|
||||
namespace OpenTK
|
||||
{
|
||||
public interface IGraphicsContext
|
||||
{
|
||||
void MakeCurrent();
|
||||
void SwapBuffers();
|
||||
|
||||
void ClearCurrent();
|
||||
}
|
||||
|
||||
public abstract class GraphicsContext : IGraphicsContext
|
||||
{
|
||||
public static IntPtr Display{ get; set; }
|
||||
|
||||
public abstract void MakeCurrent();
|
||||
|
||||
public abstract void SwapBuffers();
|
||||
|
||||
public static IGraphicsContext GetCurrentContext(IntPtr handle)
|
||||
{
|
||||
var currentPlatform = CurrentPlatform;
|
||||
|
||||
if(currentPlatform == OSPlatform.Windows){
|
||||
return WglGraphicsContext.GetCurrent(handle);
|
||||
}
|
||||
else if(currentPlatform == OSPlatform.Linux){
|
||||
if (Display == null || Display == IntPtr.Zero)
|
||||
{
|
||||
throw new InvalidOperationException("No Display set");
|
||||
}
|
||||
return GlxGraphicsContext.GetCurrent(handle, Display);
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
public abstract void ClearCurrent();
|
||||
}
|
||||
|
||||
public class WglGraphicsContext : GraphicsContext
|
||||
{
|
||||
private IntPtr _windowHandle;
|
||||
private IntPtr _deviceContext;
|
||||
|
||||
public WglGraphicsContext(IntPtr deviceContext, IntPtr graphicsContext, IntPtr windowHandle = default)
|
||||
{
|
||||
_deviceContext = deviceContext;
|
||||
_graphicsContext = graphicsContext;
|
||||
_windowHandle = windowHandle;
|
||||
}
|
||||
|
||||
private IntPtr _graphicsContext;
|
||||
|
||||
public static WglGraphicsContext GetCurrent(IntPtr windowHandle)
|
||||
{
|
||||
IntPtr dc = UnsafeNativeMethods.wglGetCurrentDC();
|
||||
IntPtr gc = UnsafeNativeMethods.wglGetCurrentContext();
|
||||
|
||||
return new WglGraphicsContext(dc, gc, windowHandle);
|
||||
}
|
||||
|
||||
public override void MakeCurrent()
|
||||
{
|
||||
UnsafeNativeMethods.WglMakeCurrent(_deviceContext, _graphicsContext);
|
||||
}
|
||||
|
||||
public override void SwapBuffers()
|
||||
{
|
||||
UnsafeNativeMethods.wglSwapBuffers(_deviceContext);
|
||||
}
|
||||
|
||||
public override void ClearCurrent()
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
}
|
||||
|
||||
public class GlxGraphicsContext : GraphicsContext
|
||||
{
|
||||
private IntPtr _windowHandle;
|
||||
|
||||
private IntPtr _drawable;
|
||||
|
||||
public static GlxGraphicsContext GetCurrent(IntPtr windowHandle, IntPtr display)
|
||||
{
|
||||
var gc = UnsafeNativeMethods.glXGetCurrentContext();
|
||||
|
||||
return new GlxGraphicsContext(windowHandle, gc, display);
|
||||
}
|
||||
|
||||
public GlxGraphicsContext(IntPtr windowHandle, IntPtr graphicsContext, IntPtr display)
|
||||
{
|
||||
_windowHandle = UnsafeNativeMethods.gdk_x11_window_get_xid(windowHandle);
|
||||
_display = UnsafeNativeMethods.gdk_x11_display_get_xdisplay(display);
|
||||
_graphicsContext = graphicsContext;
|
||||
}
|
||||
|
||||
private IntPtr _graphicsContext;
|
||||
private IntPtr _display;
|
||||
|
||||
public override void MakeCurrent()
|
||||
{
|
||||
UnsafeNativeMethods.glXMakeCurrent(_display, _windowHandle, _graphicsContext);
|
||||
}
|
||||
|
||||
public override void SwapBuffers()
|
||||
{
|
||||
UnsafeNativeMethods.glXSwapBuffers(_display, _windowHandle);
|
||||
}
|
||||
|
||||
public override void ClearCurrent()
|
||||
{
|
||||
UnsafeNativeMethods.glXMakeCurrent(_display, _windowHandle, IntPtr.Zero);
|
||||
}
|
||||
}
|
||||
}
|
Loading…
Reference in a new issue