Cocoa bindings through libobjc.dylib

This commit is contained in:
Olle Håkansson 2014-04-18 22:30:50 +02:00 committed by thefiddler
parent 4ce1289d85
commit 5e1b7c82ab
15 changed files with 987 additions and 4 deletions

View file

@ -803,6 +803,18 @@
<Compile Include="Input\HatPosition.cs" />
<Compile Include="Input\JoystickHatState.cs" />
<Compile Include="Input\KeyModifiers.cs" />
<Compile Include="Platform\MacOS\CocoaContext.cs" />
<Compile Include="Platform\MacOS\CocoaNativeWindow.cs" />
<Compile Include="Platform\MacOS\CocoaWindowInfo.cs" />
<Compile Include="Platform\MacOS\Cocoa\Cocoa.cs" />
<Compile Include="Platform\MacOS\Cocoa\Class.cs" />
<Compile Include="Platform\MacOS\Cocoa\Selector.cs" />
<Compile Include="Platform\MacOS\Cocoa\NSApplication.cs" />
<Compile Include="Platform\MacOS\Cocoa\NSApplicationActivationPolicy.cs" />
<Compile Include="Platform\MacOS\Cocoa\NSBackingStore.cs" />
<Compile Include="Platform\MacOS\Cocoa\NSWindowStyle.cs" />
<Compile Include="Platform\MacOS\Cocoa\NSOpenGLPixelFormatAttribute.cs" />
<Compile Include="Platform\MacOS\Cocoa\NSOpenGLProfile.cs" />
</ItemGroup>
<Import Project="$(MSBuildBinPath)\Microsoft.CSharp.targets" />
<PropertyGroup>
@ -832,4 +844,7 @@
</Properties>
</MonoDevelop>
</ProjectExtensions>
<ItemGroup>
<Folder Include="Platform\MacOS\Cocoa\" />
</ItemGroup>
</Project>

View file

@ -0,0 +1,21 @@
using System.Runtime.InteropServices;
using System;
namespace OpenTK.Platform.MacOS
{
static class Class
{
[DllImport (Cocoa.LibObjC)]
extern static IntPtr objc_getClass(string name);
public static IntPtr Get(string name)
{
var id = objc_getClass(name);
if (id == IntPtr.Zero)
{
throw new ArgumentException("Unknown class: " + name);
}
return id;
}
}
}

View file

@ -0,0 +1,93 @@
using System.Runtime.InteropServices;
using System;
using System.Drawing;
namespace OpenTK.Platform.MacOS
{
static class Cocoa
{
internal const string LibObjC = "/usr/lib/libobjc.dylib";
[DllImport(LibObjC, EntryPoint="objc_msgSend")]
public extern static IntPtr SendIntPtr(IntPtr receiver, IntPtr selector);
[DllImport(LibObjC, EntryPoint="objc_msgSend")]
public extern static IntPtr SendIntPtr(IntPtr receiver, IntPtr selector, IntPtr intPtr1);
[DllImport(LibObjC, EntryPoint="objc_msgSend")]
public extern static IntPtr SendIntPtr(IntPtr receiver, IntPtr selector, IntPtr intPtr1, int int1);
[DllImport(LibObjC, EntryPoint="objc_msgSend")]
public extern static IntPtr SendIntPtr(IntPtr receiver, IntPtr selector, IntPtr intPtr1, IntPtr intPtr2);
[DllImport(LibObjC, EntryPoint="objc_msgSend")]
public extern static IntPtr SendIntPtr(IntPtr receiver, IntPtr selector, RectangleF rectangle1, int int1, int int2, bool bool1);
[DllImport(LibObjC, EntryPoint="objc_msgSend")]
public extern static IntPtr SendIntPtr(IntPtr receiver, IntPtr selector, uint mask, IntPtr intPtr1, IntPtr intPtr2, bool bool1);
[DllImport(LibObjC, EntryPoint="objc_msgSend")]
public extern static bool SendBool(IntPtr receiver, IntPtr selector, int int1);
[DllImport(LibObjC, EntryPoint="objc_msgSend")]
public extern static void SendVoid(IntPtr receiver, IntPtr selector);
[DllImport(LibObjC, EntryPoint="objc_msgSend")]
public extern static void SendVoid(IntPtr receiver, IntPtr selector, IntPtr intPtr1);
[DllImport(LibObjC, EntryPoint="objc_msgSend")]
public extern static void SendVoid(IntPtr receiver, IntPtr selector, int int1);
[DllImport(LibObjC, EntryPoint="objc_msgSend")]
public extern static void SendVoid(IntPtr receiver, IntPtr selector, bool bool1);
[DllImport(LibObjC, EntryPoint="objc_msgSend")]
public extern static void SendVoid(IntPtr receiver, IntPtr selector, PointF point1);
public static IntPtr ToNative(string str)
{
if (str == null)
return IntPtr.Zero;
unsafe
{
fixed (char* ptrFirstChar = str)
{
var handle = Cocoa.SendIntPtr(Class.Get("NSString"), Selector.Alloc);
handle = Cocoa.SendIntPtr(handle, Selector.Get("initWithCharacters:length:"), (IntPtr)ptrFirstChar, str.Length);
return handle;
}
}
}
public static IntPtr GetStringConstant(IntPtr handle, string symbol)
{
var indirect = NS.GetSymbol(handle, symbol);
if (indirect == IntPtr.Zero)
return IntPtr.Zero;
var actual = Marshal.ReadIntPtr(indirect);
if (actual == IntPtr.Zero)
return IntPtr.Zero;
return actual;
//return (NSString) Runtime.GetNSObject (actual);
}
public static IntPtr AppKitLibrary;
public static IntPtr FoundationLibrary;
public static void Initialize()
{
if (AppKitLibrary != IntPtr.Zero)
{
return;
}
AppKitLibrary = NS.LoadLibrary("/System/Library/Frameworks/AppKit.framework/AppKit");
FoundationLibrary = NS.LoadLibrary("/System/Library/Frameworks/Foundation.framework/Foundation");
NSApplication.Initialize();
}
}
}

View file

@ -0,0 +1,37 @@
using System;
using System.Runtime.InteropServices;
using OpenTK.Platform.MacOS;
namespace OpenTK.Platform.MacOS
{
static class NSApplication
{
internal static IntPtr Handle;
internal static void Initialize()
{
// Create the NSAutoreleasePool
Cocoa.SendIntPtr(Cocoa.SendIntPtr(Class.Get("NSAutoreleasePool"), Selector.Alloc),
Selector.Init);
// Fetch the application handle
Handle = Cocoa.SendIntPtr(Class.Get("NSApplication"), Selector.Get("sharedApplication"));
// Setup the application
Cocoa.SendBool(Handle, Selector.Get("setActivationPolicy:"), (int)NSApplicationActivationPolicy.Regular);
Cocoa.SendVoid(Handle, Selector.Get("activateIgnoringOtherApps:"), true);
Cocoa.SendVoid(Handle, Selector.Get("finishLaunching"));
// Create the menu bar
var menubar = Cocoa.SendIntPtr(Cocoa.SendIntPtr(Class.Get("NSMenu"), Selector.Alloc),
Selector.Autorelease);
var menuItem = Cocoa.SendIntPtr(Cocoa.SendIntPtr(Class.Get("NSMenuItem"), Selector.Alloc),
Selector.Autorelease);
// Add menu item to bar, and bar to application
Cocoa.SendIntPtr(menubar, Selector.Get("addItem:"), menuItem);
Cocoa.SendIntPtr(Handle, Selector.Get("setMainMenu:"), menubar);
}
}
}

View file

@ -0,0 +1,9 @@
namespace OpenTK.Platform.MacOS
{
enum NSApplicationActivationPolicy
{
Regular,
Accessory,
Prohibited,
}
}

View file

@ -0,0 +1,9 @@
namespace OpenTK.Platform.MacOS
{
enum NSBackingStore
{
Retained,
Nonretained,
Buffered,
}
}

View file

@ -0,0 +1,47 @@
using System;
namespace OpenTK.Platform.MacOS
{
enum NSOpenGLPixelFormatAttribute
{
AllRenderers = 1,
TrippleBuffer = 3, // Lion
DoubleBuffer = 5,
Stereo = 6,
AuxBuffers = 7,
ColorSize = 8,
AlphaSize = 11,
DepthSize = 12,
StencilSize = 13,
AccumSize = 14,
MinimumPolicy = 51,
MaximumPolicy = 52,
OffScreen = 53,
FullScreen = 54,
SampleBuffers = 55,
Samples = 56,
AuxDepthStencil = 57,
ColorFloat = 58,
Multisample = 59,
Supersample = 60,
SampleAlpha = 61,
RendererID = 70,
SingleRenderer = 71,
NoRecovery = 72,
Accelerated = 73,
ClosestPolicy = 74,
[Obsolete] Robust = 75,
BackingStore = 76,
[Obsolete] MPSafe = 78,
Window = 80,
[Obsolete] MultiScreen = 81,
Compliant = 83,
ScreenMask = 84,
PixelBuffer = 90,
RemotePixelBuffer = 91,
AllowOfflineRenderers = 96,
AcceleratedCompute = 97,
OpenGLProfile = 99, // Lion
VirtualScreenCount = 128,
}
}

View file

@ -0,0 +1,8 @@
namespace OpenTK.Platform.MacOS
{
enum NSOpenGLProfile
{
VersionLegacy = 4096,
Version3_2Core = 12800,
}
}

View file

@ -0,0 +1,22 @@
using System;
namespace OpenTK.Platform.MacOS
{
[Flags]
public enum NSWindowStyle
{
Borderless = 0,
Titled = 1,
Closable = 2,
Miniaturizable = 4,
Resizable = 8,
Utility = 16,
DocModal = 64,
NonactivatingPanel = 128,
TexturedBackground = 256,
Unscaled = 2048,
UnifiedTitleAndToolbar = 4096,
Hud = 8192,
FullScreenWindow = 16384,
}
}

View file

@ -0,0 +1,18 @@
using System;
using System.Runtime.InteropServices;
namespace OpenTK.Platform.MacOS
{
static class Selector
{
// Frequently used selectors
public static readonly IntPtr Init = Selector.Get("init");
public static readonly IntPtr InitWithCoder = Selector.Get("initWithCoder:");
public static readonly IntPtr Alloc = Selector.Get("alloc");
public static readonly IntPtr Release = Selector.Get("release");
public static readonly IntPtr Autorelease = Selector.Get("autorelease");
[DllImport ("/usr/lib/libobjc.dylib", EntryPoint="sel_registerName")]
public extern static IntPtr Get(string name);
}
}

View file

@ -0,0 +1,263 @@
using System;
using OpenTK.Platform;
using OpenTK.Graphics;
using OpenTK.Platform.MacOS;
using System.Diagnostics;
using System.Collections.Generic;
using System.Runtime.InteropServices;
namespace OpenTK
{
class CocoaContext : DesktopGraphicsContext
{
private CocoaWindowInfo cocoaWindow;
private IntPtr shareContextRef;
static readonly IntPtr NSOpenGLContext = Class.Get("NSOpenGLContext");
static readonly IntPtr currentContext = Selector.Get("currentContext");
static readonly IntPtr flushBuffer = Selector.Get("flushBuffer");
static readonly IntPtr makeCurrentContext = Selector.Get("makeCurrentContext");
static readonly IntPtr update = Selector.Get("update");
static CocoaContext()
{
Cocoa.Initialize();
}
public CocoaContext(GraphicsMode mode, IWindowInfo window, IGraphicsContext shareContext, int majorVersion, int minorVersion)
{
Debug.Print("Context Type: {0}", shareContext);
Debug.Print("Window info: {0}", window);
cocoaWindow = (CocoaWindowInfo)window;
if (shareContext is CocoaContext)
shareContextRef = ((CocoaContext)shareContext).Handle.Handle;
if (shareContext is GraphicsContext)
{
ContextHandle shareHandle = shareContext != null ? (shareContext as IGraphicsContextInternal).Context : (ContextHandle)IntPtr.Zero;
shareContextRef = shareHandle.Handle;
}
if (shareContextRef == IntPtr.Zero)
{
Debug.Print("No context sharing will take place.");
}
CreateContext(mode, cocoaWindow, shareContextRef, majorVersion, minorVersion, true);
}
public CocoaContext(ContextHandle handle, IWindowInfo window, IGraphicsContext shareContext, int majorVersion, int minorVersion)
{
if (handle == ContextHandle.Zero)
throw new ArgumentException("handle");
if (window == null)
throw new ArgumentNullException("window");
Handle = handle;
cocoaWindow = (CocoaWindowInfo)window;
}
private void AddPixelAttrib(List<NSOpenGLPixelFormatAttribute> attributes, NSOpenGLPixelFormatAttribute attribute)
{
Debug.Print(attribute.ToString());
attributes.Add(attribute);
}
private void AddPixelAttrib(List<NSOpenGLPixelFormatAttribute> attributes, NSOpenGLPixelFormatAttribute attribute, int value)
{
Debug.Print("{0} : {1}", attribute, value);
attributes.Add(attribute);
attributes.Add((NSOpenGLPixelFormatAttribute)value);
}
private void CreateContext(GraphicsMode mode, CocoaWindowInfo cocoaWindow, IntPtr shareContextRef, int majorVersion, int minorVersion, bool fullscreen)
{
// Prepare attributes
List<NSOpenGLPixelFormatAttribute> attributes = new List<NSOpenGLPixelFormatAttribute>();
var profile = NSOpenGLProfile.VersionLegacy;
if (majorVersion > 3 || (majorVersion == 3 && minorVersion >= 2))
{
profile = NSOpenGLProfile.Version3_2Core;
Debug.Print("Running the OpenGL core profile.");
}
else
{
Debug.Print("Running the legacy OpenGL profile. Start with version major=3, minor=2 or later for the 3.2 profile.");
}
Debug.Print("NSGL pixel format attributes:");
Debug.Indent();
AddPixelAttrib(attributes, NSOpenGLPixelFormatAttribute.OpenGLProfile, (int)profile);
AddPixelAttrib(attributes, NSOpenGLPixelFormatAttribute.DoubleBuffer);
AddPixelAttrib(attributes, NSOpenGLPixelFormatAttribute.Accelerated);
AddPixelAttrib(attributes, NSOpenGLPixelFormatAttribute.ColorSize, mode.ColorFormat.BitsPerPixel);
if (mode.Depth > 0)
AddPixelAttrib(attributes, NSOpenGLPixelFormatAttribute.DepthSize, mode.Depth);
if (mode.Stencil > 0)
AddPixelAttrib(attributes, NSOpenGLPixelFormatAttribute.StencilSize, mode.Stencil);
if (mode.AccumulatorFormat.BitsPerPixel > 0)
{
AddPixelAttrib(attributes, NSOpenGLPixelFormatAttribute.AccumSize, mode.AccumulatorFormat.BitsPerPixel);
}
if (mode.Samples > 1)
{
AddPixelAttrib(attributes, NSOpenGLPixelFormatAttribute.SampleBuffers, 1);
AddPixelAttrib(attributes, NSOpenGLPixelFormatAttribute.Samples, mode.Samples);
}
AddPixelAttrib(attributes, (NSOpenGLPixelFormatAttribute)0);
Debug.Unindent();
Debug.Write("Attribute array: ");
for (int i = 0; i < attributes.Count; i++)
Debug.Write(attributes[i].ToString() + " ");
Debug.WriteLine("");
// Create pixel format
var pixelFormat = Cocoa.SendIntPtr(Class.Get("NSOpenGLPixelFormat"), Selector.Alloc);
unsafe
{
fixed (NSOpenGLPixelFormatAttribute* ptr = attributes.ToArray())
{
pixelFormat = Cocoa.SendIntPtr(pixelFormat, Selector.Get("initWithAttributes:"), (IntPtr)ptr);
}
}
// Create context
var context = Cocoa.SendIntPtr(NSOpenGLContext, Selector.Alloc);
context = Cocoa.SendIntPtr(context, Selector.Get("initWithFormat:shareContext:"), pixelFormat, shareContextRef);
// Release pixel format
Cocoa.SendVoid(pixelFormat, Selector.Release);
pixelFormat = IntPtr.Zero;
// Attach the view
Cocoa.SendVoid(context, Selector.Get("setView:"), cocoaWindow.ViewHandle);
Cocoa.SendVoid(cocoaWindow.ViewHandle, Selector.Get("setWantsBestResolutionOpenGLSurface:"), true);
// Finalize
Handle = new ContextHandle(context);
Update(cocoaWindow);
MakeCurrent(cocoaWindow);
}
public override void SwapBuffers()
{
Cocoa.SendVoid(Handle.Handle, flushBuffer);
}
public override void MakeCurrent(IWindowInfo window)
{
Cocoa.SendVoid(Handle.Handle, makeCurrentContext);
}
public override bool IsCurrent
{
get
{
return Handle.Handle == CurrentContext;
}
}
public static IntPtr CurrentContext
{
get
{
return Cocoa.SendIntPtr(NSOpenGLContext, currentContext);
}
}
// private unsafe void SetContextValue (int val, NSOpenGLContextParameter par)
// {
// int *p = &val;
// context.SetValues ((IntPtr)p, par);
// }
//
// private unsafe int GetContextValue (NSOpenGLContextParameter par)
// {
// int ret;
// int *p = &ret;
// context.GetValues ((IntPtr)p, par);
//
// return ret;
// }
public override int SwapInterval
{
get
{
return 0;
//return GetContextValue(NSOpenGLContextParameter.SwapInterval);
}
set
{
//SetContextValue(value, NSOpenGLContextParameter.SwapInterval);
}
}
public override void Update(IWindowInfo window)
{
Cocoa.SendVoid(Handle.Handle, update);
}
#region IDisposable Members
~CocoaContext()
{
Dispose(false);
}
public override void Dispose()
{
Dispose(true);
}
void Dispose(bool disposing)
{
if (IsDisposed || Handle.Handle == IntPtr.Zero)
return;
Debug.Print("Disposing of Cocoa context.");
Cocoa.SendIntPtr(NSOpenGLContext, Selector.Get("clearCurrentContext"));
// NSOpenGLContext.ClearCurrentContext();
// context.ClearDrawable();
// context.Dispose();
// context = null;
Handle = ContextHandle.Zero;
IsDisposed = true;
}
#endregion
#region IGraphicsContextInternal Members
public override IntPtr GetAddress(string function)
{
return NS.GetAddress(function);
}
public override IntPtr GetAddress(IntPtr function)
{
return NS.GetAddress(function);
}
#endregion
}
}

View file

@ -0,0 +1,306 @@
using System;
using OpenTK.Graphics;
namespace OpenTK.Platform.MacOS
{
class CocoaNativeWindow : INativeWindow
{
public event System.EventHandler<System.EventArgs> Move;
public event System.EventHandler<System.EventArgs> Resize;
public event System.EventHandler<System.ComponentModel.CancelEventArgs> Closing;
public event System.EventHandler<System.EventArgs> Closed;
public event System.EventHandler<System.EventArgs> Disposed;
public event System.EventHandler<System.EventArgs> IconChanged;
public event System.EventHandler<System.EventArgs> TitleChanged;
public event System.EventHandler<System.EventArgs> VisibleChanged;
public event System.EventHandler<System.EventArgs> FocusedChanged;
public event System.EventHandler<System.EventArgs> WindowBorderChanged;
public event System.EventHandler<System.EventArgs> WindowStateChanged;
public event System.EventHandler<OpenTK.Input.KeyboardKeyEventArgs> KeyDown;
public event System.EventHandler<KeyPressEventArgs> KeyPress;
public event System.EventHandler<OpenTK.Input.KeyboardKeyEventArgs> KeyUp;
public event System.EventHandler<System.EventArgs> MouseLeave;
public event System.EventHandler<System.EventArgs> MouseEnter;
private CocoaWindowInfo windowInfo;
static readonly IntPtr nextEventMatchingMask = Selector.Get("nextEventMatchingMask:untilDate:inMode:dequeue:");
static readonly IntPtr sendEvent = Selector.Get("sendEvent:");
static readonly IntPtr updateWindows = Selector.Get("updateWindows");
static readonly IntPtr contentView = Selector.Get("contentView");
static readonly IntPtr NSDefaultRunLoopMode;
static CocoaNativeWindow()
{
Cocoa.Initialize();
NSDefaultRunLoopMode = Cocoa.GetStringConstant(Cocoa.FoundationLibrary, "NSDefaultRunLoopMode");
}
public CocoaNativeWindow(int x, int y, int width, int height, string title, GraphicsMode mode, GameWindowFlags options, DisplayDevice device)
{
var contentRect = new System.Drawing.RectangleF(x, y, width, height);
var style = NSWindowStyle.Titled | NSWindowStyle.Resizable;
var bufferingType = NSBackingStore.Buffered;
IntPtr windowPtr;
windowPtr = Cocoa.SendIntPtr(Class.Get("NSWindow"), Selector.Alloc);
windowPtr = Cocoa.SendIntPtr(windowPtr, Selector.Get("initWithContentRect:styleMask:backing:defer:"), contentRect, (int)style, (int)bufferingType, false);
windowPtr = Cocoa.SendIntPtr(windowPtr, Selector.Autorelease);
Cocoa.SendVoid(windowPtr, Selector.Get("cascadeTopLeftFromPoint:"), new System.Drawing.PointF(20, 20));
Cocoa.SendVoid(windowPtr, Selector.Get("setTitle:"), Cocoa.ToNative(title));
Cocoa.SendVoid(windowPtr, Selector.Get("makeKeyAndOrderFront:"), IntPtr.Zero);
windowInfo = new CocoaWindowInfo(windowPtr);
}
public static IntPtr GetView(IntPtr windowHandle)
{
return Cocoa.SendIntPtr(windowHandle, contentView);
}
public void Close()
{
throw new System.NotImplementedException();
}
public void ProcessEvents()
{
var e = Cocoa.SendIntPtr(NSApplication.Handle, nextEventMatchingMask, uint.MaxValue, IntPtr.Zero, NSDefaultRunLoopMode, true);
if (e == IntPtr.Zero)
return;
Cocoa.SendVoid(NSApplication.Handle, sendEvent, e);
Cocoa.SendVoid(NSApplication.Handle, updateWindows);
}
public System.Drawing.Point PointToClient(System.Drawing.Point point)
{
throw new System.NotImplementedException();
}
public System.Drawing.Point PointToScreen(System.Drawing.Point point)
{
throw new System.NotImplementedException();
}
public System.Drawing.Icon Icon
{
get
{
throw new System.NotImplementedException();
}
set
{
throw new System.NotImplementedException();
}
}
public string Title
{
get
{
throw new System.NotImplementedException();
}
set
{
throw new System.NotImplementedException();
}
}
public bool Focused
{
get
{
throw new System.NotImplementedException();
}
}
public bool Visible
{
get
{
//throw new System.NotImplementedException();
return true;
}
set
{
//throw new System.NotImplementedException();
}
}
public bool Exists
{
get
{
return true;
}
}
public IWindowInfo WindowInfo
{
get
{
return windowInfo;
}
}
public WindowState WindowState
{
get
{
throw new System.NotImplementedException();
}
set
{
throw new System.NotImplementedException();
}
}
public WindowBorder WindowBorder
{
get
{
throw new System.NotImplementedException();
}
set
{
throw new System.NotImplementedException();
}
}
public System.Drawing.Rectangle Bounds
{
get
{
throw new System.NotImplementedException();
}
set
{
throw new System.NotImplementedException();
}
}
public System.Drawing.Point Location
{
get
{
throw new System.NotImplementedException();
}
set
{
throw new System.NotImplementedException();
}
}
public System.Drawing.Size Size
{
get
{
throw new System.NotImplementedException();
}
set
{
throw new System.NotImplementedException();
}
}
public int X
{
get
{
throw new System.NotImplementedException();
}
set
{
throw new System.NotImplementedException();
}
}
public int Y
{
get
{
throw new System.NotImplementedException();
}
set
{
throw new System.NotImplementedException();
}
}
public int Width
{
get
{
throw new System.NotImplementedException();
}
set
{
throw new System.NotImplementedException();
}
}
public int Height
{
get
{
throw new System.NotImplementedException();
}
set
{
throw new System.NotImplementedException();
}
}
public System.Drawing.Rectangle ClientRectangle
{
get
{
throw new System.NotImplementedException();
}
set
{
throw new System.NotImplementedException();
}
}
public System.Drawing.Size ClientSize
{
get
{
throw new System.NotImplementedException();
}
set
{
throw new System.NotImplementedException();
}
}
public OpenTK.Input.IInputDriver InputDriver
{
get
{
throw new System.NotImplementedException();
}
}
public bool CursorVisible
{
get
{
throw new System.NotImplementedException();
}
set
{
throw new System.NotImplementedException();
}
}
public void Dispose()
{
}
}
}

View file

@ -0,0 +1,113 @@
#region License
//
// The Open Toolkit Library License
//
// Copyright (c) 2006 - 2009 the Open Toolkit library.
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to deal
// in the Software without restriction, including without limitation the rights to
// use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
// the Software, and to permit persons to whom the Software is furnished to do
// so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all
// copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
// HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
// WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
// OTHER DEALINGS IN THE SOFTWARE.
//
#endregion
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Text;
namespace OpenTK.Platform.MacOS
{
/// \internal
/// <summary>
/// Describes a Cocoa window.
/// </summary>
sealed class CocoaWindowInfo : IWindowInfo
{
IntPtr nsWindowRef;
bool disposed = false;
#region Constructors
/// <summary>
/// Constructs a new instance with the specified parameters.
/// </summary>
/// <param name="nsWindowRef">A valid NSView reference.</param>
public CocoaWindowInfo(IntPtr nsWindowRef)
{
this.nsWindowRef = nsWindowRef;
}
#endregion
#region Public Members
/// <summary>
/// Gets the window reference for this instance.
/// </summary>
public IntPtr Handle { get { return nsWindowRef; } }
/// <summary>
/// Gets the view reference for this instance.
/// </summary>
public IntPtr ViewHandle
{
get
{
return CocoaNativeWindow.GetView(nsWindowRef);
}
}
/// <summary>Returns a System.String that represents the current window.</summary>
/// <returns>A System.String that represents the current window.</returns>
public override string ToString()
{
return String.Format("MacOS.CocoaWindowInfo: NSWindow {0}", nsWindowRef);
}
#endregion
#region IDisposable Members
public void Dispose()
{
Dispose(true);
}
void Dispose(bool disposing)
{
if (disposed)
return;
if (disposing)
{
}
disposed = true;
}
~CocoaWindowInfo()
{
Dispose(false);
}
#endregion
}
}

View file

@ -43,7 +43,7 @@ namespace OpenTK.Platform.MacOS
public override INativeWindow CreateNativeWindow(int x, int y, int width, int height, string title, GraphicsMode mode, GameWindowFlags options, DisplayDevice device)
{
return new CarbonGLNative(x, y, width, height, title, mode, options, device);
return new CocoaNativeWindow(x, y, width, height, title, mode, options, device);
}
public override IDisplayDeviceDriver CreateDisplayDeviceDriver()
@ -53,19 +53,19 @@ namespace OpenTK.Platform.MacOS
public override IGraphicsContext CreateGLContext(GraphicsMode mode, IWindowInfo window, IGraphicsContext shareContext, bool directRendering, int major, int minor, GraphicsContextFlags flags)
{
return new AglContext(mode, window, shareContext);
return new CocoaContext(mode, window, shareContext, major, minor);
}
public override IGraphicsContext CreateGLContext(ContextHandle handle, IWindowInfo window, IGraphicsContext shareContext, bool directRendering, int major, int minor, GraphicsContextFlags flags)
{
return new AglContext(handle, window, shareContext);
return new CocoaContext(handle, window, shareContext, major, minor);
}
public override GraphicsContext.GetCurrentContextDelegate CreateGetCurrentGraphicsContext()
{
return (GraphicsContext.GetCurrentContextDelegate)delegate
{
return new ContextHandle(Cgl.GetCurrentContext());
return new ContextHandle(CocoaContext.CurrentContext);
};
}

View file

@ -48,6 +48,12 @@ namespace OpenTK.Platform.MacOS
static extern IntPtr NSLookupAndBindSymbol(IntPtr s);
[DllImport(Library, EntryPoint = "NSAddressOfSymbol")]
static extern IntPtr NSAddressOfSymbol(IntPtr symbol);
[DllImport(Library)]
private static extern IntPtr dlopen(String fileName, int flags);
[DllImport(Library)]
private static extern int dlclose(IntPtr handle);
[DllImport (Library)]
private static extern IntPtr dlsym (IntPtr handle, string symbol);
public static IntPtr GetAddress(string function)
{
@ -87,6 +93,22 @@ namespace OpenTK.Platform.MacOS
}
return symbol;
}
public static IntPtr GetSymbol(IntPtr handle, string symbol)
{
return dlsym(handle, symbol);
}
public static IntPtr LoadLibrary(string fileName)
{
const int RTLD_NOW = 2;
return dlopen(fileName, RTLD_NOW);
}
public static void FreeLibrary(IntPtr handle)
{
dlclose(handle);
}
}
}