mirror of
https://github.com/Ryujinx/Opentk.git
synced 2025-06-03 00:30:21 +00:00
Improved resource disposal
Added IDisposable interface to all classes holding native data that must be freed. OpenTK.Toolkit.Init() now returns an IDisposable instance that can be used to cleanup all native data held by OpenTK. This is useful when re-initializing OpenTK (possibly in a new AppDomain), as is the case in the Example browser.
This commit is contained in:
parent
ff9cd61777
commit
a85cecdc59
|
@ -1,41 +1,41 @@
|
||||||
#region License
|
#region License
|
||||||
//
|
//
|
||||||
// The Open Toolkit Library License
|
// The Open Toolkit Library License
|
||||||
//
|
//
|
||||||
// Copyright (c) 2006 - 2010 the Open Toolkit library.
|
// Copyright (c) 2006 - 2010 the Open Toolkit library.
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
// of this software and associated documentation files (the "Software"), to deal
|
// of this software and associated documentation files (the "Software"), to deal
|
||||||
// in the Software without restriction, including without limitation the rights to
|
// in the Software without restriction, including without limitation the rights to
|
||||||
// use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
|
// 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
|
// the Software, and to permit persons to whom the Software is furnished to do
|
||||||
// so, subject to the following conditions:
|
// so, subject to the following conditions:
|
||||||
//
|
//
|
||||||
// The above copyright notice and this permission notice shall be included in all
|
// The above copyright notice and this permission notice shall be included in all
|
||||||
// copies or substantial portions of the Software.
|
// copies or substantial portions of the Software.
|
||||||
//
|
//
|
||||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
||||||
// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
|
// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
|
||||||
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
||||||
// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
|
// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
|
||||||
// HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
// HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||||
// WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
// WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
|
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
|
||||||
// OTHER DEALINGS IN THE SOFTWARE.
|
// OTHER DEALINGS IN THE SOFTWARE.
|
||||||
//
|
//
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Text;
|
using System.Text;
|
||||||
|
|
||||||
namespace OpenTK.Input
|
namespace OpenTK.Input
|
||||||
{
|
{
|
||||||
// Defines the interface for a 2nd generation input driver.
|
// Defines the interface for a 2nd generation input driver.
|
||||||
interface IInputDriver2
|
interface IInputDriver2 : IDisposable
|
||||||
{
|
{
|
||||||
IMouseDriver2 MouseDriver { get; }
|
IMouseDriver2 MouseDriver { get; }
|
||||||
IKeyboardDriver2 KeyboardDriver { get; }
|
IKeyboardDriver2 KeyboardDriver { get; }
|
||||||
IGamePadDriver GamePadDriver { get; }
|
IGamePadDriver GamePadDriver { get; }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -27,6 +27,7 @@
|
||||||
|
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
using System.Diagnostics;
|
||||||
using System.Text;
|
using System.Text;
|
||||||
|
|
||||||
namespace OpenTK.Platform
|
namespace OpenTK.Platform
|
||||||
|
@ -37,6 +38,7 @@ namespace OpenTK.Platform
|
||||||
{
|
{
|
||||||
#region Fields
|
#region Fields
|
||||||
|
|
||||||
|
bool disposed;
|
||||||
static IPlatformFactory default_implementation, embedded_implementation;
|
static IPlatformFactory default_implementation, embedded_implementation;
|
||||||
|
|
||||||
#endregion
|
#endregion
|
||||||
|
@ -133,7 +135,8 @@ namespace OpenTK.Platform
|
||||||
class UnsupportedPlatform : IPlatformFactory
|
class UnsupportedPlatform : IPlatformFactory
|
||||||
{
|
{
|
||||||
#region Fields
|
#region Fields
|
||||||
|
|
||||||
|
bool disposed;
|
||||||
static readonly string error_string = "Please, refer to http://www.opentk.com for more information.";
|
static readonly string error_string = "Please, refer to http://www.opentk.com for more information.";
|
||||||
|
|
||||||
#endregion
|
#endregion
|
||||||
|
@ -191,6 +194,72 @@ namespace OpenTK.Platform
|
||||||
}
|
}
|
||||||
|
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
|
#region IDisposable Members
|
||||||
|
|
||||||
|
void Dispose(bool manual)
|
||||||
|
{
|
||||||
|
if (!disposed)
|
||||||
|
{
|
||||||
|
if (manual)
|
||||||
|
{
|
||||||
|
// nothing to do
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Debug.Print("{0} leaked, did you forget to call Dispose()?", GetType());
|
||||||
|
}
|
||||||
|
disposed = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void Dispose()
|
||||||
|
{
|
||||||
|
Dispose(true);
|
||||||
|
GC.SuppressFinalize(this);
|
||||||
|
}
|
||||||
|
|
||||||
|
~UnsupportedPlatform()
|
||||||
|
{
|
||||||
|
Dispose(false);
|
||||||
|
}
|
||||||
|
|
||||||
|
#endregion
|
||||||
|
}
|
||||||
|
|
||||||
|
#endregion
|
||||||
|
|
||||||
|
#region IDisposable Members
|
||||||
|
|
||||||
|
void Dispose(bool manual)
|
||||||
|
{
|
||||||
|
if (!disposed)
|
||||||
|
{
|
||||||
|
if (manual)
|
||||||
|
{
|
||||||
|
Default.Dispose();
|
||||||
|
if (Embedded != Default)
|
||||||
|
{
|
||||||
|
Embedded.Dispose();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Debug.Print("{0} leaked, did you forget to call Dispose()?", GetType());
|
||||||
|
}
|
||||||
|
disposed = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void Dispose()
|
||||||
|
{
|
||||||
|
Dispose(true);
|
||||||
|
GC.SuppressFinalize(this);
|
||||||
|
}
|
||||||
|
|
||||||
|
~Factory()
|
||||||
|
{
|
||||||
|
Dispose(false);
|
||||||
}
|
}
|
||||||
|
|
||||||
#endregion
|
#endregion
|
||||||
|
|
|
@ -33,7 +33,7 @@ using OpenTK.Graphics;
|
||||||
|
|
||||||
namespace OpenTK.Platform
|
namespace OpenTK.Platform
|
||||||
{
|
{
|
||||||
interface IPlatformFactory
|
interface IPlatformFactory : IDisposable
|
||||||
{
|
{
|
||||||
INativeWindow CreateNativeWindow(int x, int y, int width, int height, string title, GraphicsMode mode, GameWindowFlags options, DisplayDevice device);
|
INativeWindow CreateNativeWindow(int x, int y, int width, int height, string title, GraphicsMode mode, GameWindowFlags options, DisplayDevice device);
|
||||||
|
|
||||||
|
|
|
@ -120,28 +120,32 @@ namespace OpenTK.Platform.MacOS.Carbon
|
||||||
|
|
||||||
switch (evt.EventClass)
|
switch (evt.EventClass)
|
||||||
{
|
{
|
||||||
case EventClass.Application:
|
case EventClass.Application:
|
||||||
switch (evt.AppEventKind)
|
switch (evt.AppEventKind)
|
||||||
{
|
{
|
||||||
default:
|
case AppEventKind.AppQuit:
|
||||||
return OSStatus.EventNotHandled;
|
API.RemoveEventHandler(uppHandler);
|
||||||
}
|
return OSStatus.EventNotHandled;
|
||||||
|
|
||||||
|
default:
|
||||||
|
return OSStatus.EventNotHandled;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
case EventClass.AppleEvent:
|
case EventClass.AppleEvent:
|
||||||
// only event here is the apple event.
|
// only event here is the apple event.
|
||||||
Debug.Print("Processing apple event.");
|
Debug.Print("Processing apple event.");
|
||||||
API.ProcessAppleEvent(inEvent);
|
API.ProcessAppleEvent(inEvent);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case EventClass.Keyboard:
|
case EventClass.Keyboard:
|
||||||
case EventClass.Mouse:
|
case EventClass.Mouse:
|
||||||
if (WindowEventHandler != null)
|
if (WindowEventHandler != null)
|
||||||
{
|
{
|
||||||
return WindowEventHandler.DispatchEvent(inCaller, inEvent, evt, userData);
|
return WindowEventHandler.DispatchEvent(inCaller, inEvent, evt, userData);
|
||||||
}
|
}
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
return OSStatus.EventNotHandled;
|
return OSStatus.EventNotHandled;
|
||||||
|
|
|
@ -175,8 +175,8 @@ namespace OpenTK.Platform.MacOS
|
||||||
{
|
{
|
||||||
if (uppHandler != IntPtr.Zero)
|
if (uppHandler != IntPtr.Zero)
|
||||||
{
|
{
|
||||||
//API.RemoveEventHandler(uppHandler);
|
API.RemoveEventHandler(uppHandler);
|
||||||
//API.DisposeEventHandlerUPP(uppHandler);
|
API.DisposeEventHandlerUPP(uppHandler);
|
||||||
}
|
}
|
||||||
|
|
||||||
uppHandler = IntPtr.Zero;
|
uppHandler = IntPtr.Zero;
|
||||||
|
@ -925,8 +925,6 @@ namespace OpenTK.Platform.MacOS
|
||||||
return;
|
return;
|
||||||
|
|
||||||
OnClosed();
|
OnClosed();
|
||||||
|
|
||||||
Dispose();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public WindowState WindowState
|
public WindowState WindowState
|
||||||
|
|
|
@ -69,9 +69,11 @@ namespace OpenTK.Platform.MacOS
|
||||||
readonly CFString InputLoopMode = CF.RunLoopModeDefault;
|
readonly CFString InputLoopMode = CF.RunLoopModeDefault;
|
||||||
readonly CFDictionary DeviceTypes = new CFDictionary();
|
readonly CFDictionary DeviceTypes = new CFDictionary();
|
||||||
|
|
||||||
readonly NativeMethods.IOHIDDeviceCallback HandleDeviceAdded;
|
NativeMethods.IOHIDDeviceCallback HandleDeviceAdded;
|
||||||
readonly NativeMethods.IOHIDDeviceCallback HandleDeviceRemoved;
|
NativeMethods.IOHIDDeviceCallback HandleDeviceRemoved;
|
||||||
readonly NativeMethods.IOHIDValueCallback HandleDeviceValueReceived;
|
NativeMethods.IOHIDValueCallback HandleDeviceValueReceived;
|
||||||
|
|
||||||
|
bool disposed;
|
||||||
|
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
|
@ -164,6 +166,7 @@ namespace OpenTK.Platform.MacOS
|
||||||
// Thanks to Jase: http://www.opentk.com/node/2800
|
// Thanks to Jase: http://www.opentk.com/node/2800
|
||||||
NativeMethods.IOHIDDeviceRegisterInputValueCallback(device,
|
NativeMethods.IOHIDDeviceRegisterInputValueCallback(device,
|
||||||
HandleDeviceValueReceived, device);
|
HandleDeviceValueReceived, device);
|
||||||
|
|
||||||
NativeMethods.IOHIDDeviceScheduleWithRunLoop(device, RunLoop, InputLoopMode);
|
NativeMethods.IOHIDDeviceScheduleWithRunLoop(device, RunLoop, InputLoopMode);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -192,12 +195,19 @@ namespace OpenTK.Platform.MacOS
|
||||||
KeyboardDevices[device] = state;
|
KeyboardDevices[device] = state;
|
||||||
}
|
}
|
||||||
|
|
||||||
NativeMethods.IOHIDDeviceRegisterInputValueCallback(device, null, IntPtr.Zero);
|
NativeMethods.IOHIDDeviceRegisterInputValueCallback(device, IntPtr.Zero, IntPtr.Zero);
|
||||||
NativeMethods.IOHIDDeviceUnscheduleWithRunLoop(device, RunLoop, InputLoopMode);
|
NativeMethods.IOHIDDeviceUnscheduleWithRunLoop(device, RunLoop, InputLoopMode);
|
||||||
}
|
}
|
||||||
|
|
||||||
void DeviceValueReceived(IntPtr context, IOReturn res, IntPtr sender, IOHIDValueRef val)
|
void DeviceValueReceived(IntPtr context, IOReturn res, IntPtr sender, IOHIDValueRef val)
|
||||||
{
|
{
|
||||||
|
if (disposed)
|
||||||
|
{
|
||||||
|
Debug.Print("DeviceValueReceived({0}, {1}, {2}, {3}) called on disposed {4}",
|
||||||
|
context, res, sender, val, GetType());
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
MouseState mouse;
|
MouseState mouse;
|
||||||
KeyboardState keyboard;
|
KeyboardState keyboard;
|
||||||
if (MouseDevices.TryGetValue(context, out mouse))
|
if (MouseDevices.TryGetValue(context, out mouse))
|
||||||
|
@ -383,6 +393,12 @@ namespace OpenTK.Platform.MacOS
|
||||||
IOHIDDeviceCallback inIOHIDDeviceCallback,
|
IOHIDDeviceCallback inIOHIDDeviceCallback,
|
||||||
IntPtr inContext);
|
IntPtr inContext);
|
||||||
|
|
||||||
|
[DllImport(hid)]
|
||||||
|
public static extern void IOHIDManagerRegisterDeviceMatchingCallback(
|
||||||
|
IOHIDManagerRef inIOHIDManagerRef,
|
||||||
|
IntPtr inIOHIDDeviceCallback,
|
||||||
|
IntPtr inContext);
|
||||||
|
|
||||||
// This routine will be called when a (matching) device is disconnected.
|
// This routine will be called when a (matching) device is disconnected.
|
||||||
[DllImport(hid)]
|
[DllImport(hid)]
|
||||||
public static extern void IOHIDManagerRegisterDeviceRemovalCallback(
|
public static extern void IOHIDManagerRegisterDeviceRemovalCallback(
|
||||||
|
@ -390,6 +406,12 @@ namespace OpenTK.Platform.MacOS
|
||||||
IOHIDDeviceCallback inIOHIDDeviceCallback,
|
IOHIDDeviceCallback inIOHIDDeviceCallback,
|
||||||
IntPtr inContext);
|
IntPtr inContext);
|
||||||
|
|
||||||
|
[DllImport(hid)]
|
||||||
|
public static extern void IOHIDManagerRegisterDeviceRemovalCallback(
|
||||||
|
IOHIDManagerRef inIOHIDManagerRef,
|
||||||
|
IntPtr inIOHIDDeviceCallback,
|
||||||
|
IntPtr inContext);
|
||||||
|
|
||||||
[DllImport(hid)]
|
[DllImport(hid)]
|
||||||
public static extern void IOHIDManagerScheduleWithRunLoop(
|
public static extern void IOHIDManagerScheduleWithRunLoop(
|
||||||
IOHIDManagerRef inIOHIDManagerRef,
|
IOHIDManagerRef inIOHIDManagerRef,
|
||||||
|
@ -428,6 +450,12 @@ namespace OpenTK.Platform.MacOS
|
||||||
IOHIDValueCallback callback,
|
IOHIDValueCallback callback,
|
||||||
IntPtr context);
|
IntPtr context);
|
||||||
|
|
||||||
|
[DllImport(hid)]
|
||||||
|
public static extern void IOHIDDeviceRegisterInputValueCallback(
|
||||||
|
IOHIDDeviceRef device,
|
||||||
|
IntPtr callback,
|
||||||
|
IntPtr context);
|
||||||
|
|
||||||
[DllImport(hid)]
|
[DllImport(hid)]
|
||||||
public static extern void IOHIDDeviceScheduleWithRunLoop(
|
public static extern void IOHIDDeviceScheduleWithRunLoop(
|
||||||
IOHIDDeviceRef device,
|
IOHIDDeviceRef device,
|
||||||
|
@ -939,6 +967,59 @@ namespace OpenTK.Platform.MacOS
|
||||||
};
|
};
|
||||||
|
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
|
#region IDisposable Members
|
||||||
|
|
||||||
|
|
||||||
|
void Dispose(bool manual)
|
||||||
|
{
|
||||||
|
if (!disposed)
|
||||||
|
{
|
||||||
|
if (manual)
|
||||||
|
{
|
||||||
|
NativeMethods.IOHIDManagerRegisterDeviceMatchingCallback(
|
||||||
|
hidmanager, IntPtr.Zero, IntPtr.Zero);
|
||||||
|
NativeMethods.IOHIDManagerRegisterDeviceRemovalCallback(
|
||||||
|
hidmanager, IntPtr.Zero, IntPtr.Zero);
|
||||||
|
NativeMethods.IOHIDManagerScheduleWithRunLoop(
|
||||||
|
hidmanager, IntPtr.Zero, IntPtr.Zero);
|
||||||
|
|
||||||
|
foreach (var device in MouseDevices.Keys)
|
||||||
|
{
|
||||||
|
NativeMethods.IOHIDDeviceRegisterInputValueCallback(
|
||||||
|
device, IntPtr.Zero, IntPtr.Zero);
|
||||||
|
}
|
||||||
|
|
||||||
|
foreach (var device in KeyboardDevices.Keys)
|
||||||
|
{
|
||||||
|
NativeMethods.IOHIDDeviceRegisterInputValueCallback(
|
||||||
|
device, IntPtr.Zero, IntPtr.Zero);
|
||||||
|
}
|
||||||
|
|
||||||
|
HandleDeviceAdded = null;
|
||||||
|
HandleDeviceRemoved = null;
|
||||||
|
HandleDeviceValueReceived = null;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Debug.Print("{0} leaked, did you forget to call Dispose()?", GetType());
|
||||||
|
}
|
||||||
|
disposed = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void Dispose()
|
||||||
|
{
|
||||||
|
Dispose(true);
|
||||||
|
GC.SuppressFinalize(this);
|
||||||
|
}
|
||||||
|
|
||||||
|
~HIDInput()
|
||||||
|
{
|
||||||
|
Dispose(false);
|
||||||
|
}
|
||||||
|
|
||||||
|
#endregion
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -27,6 +27,7 @@
|
||||||
|
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
using System.Diagnostics;
|
||||||
using System.Text;
|
using System.Text;
|
||||||
using OpenTK.Input;
|
using OpenTK.Input;
|
||||||
|
|
||||||
|
@ -38,6 +39,7 @@ namespace OpenTK.Platform.MacOS
|
||||||
{
|
{
|
||||||
#region Fields
|
#region Fields
|
||||||
|
|
||||||
|
bool disposed;
|
||||||
readonly IInputDriver2 InputDriver = new HIDInput();
|
readonly IInputDriver2 InputDriver = new HIDInput();
|
||||||
|
|
||||||
#endregion
|
#endregion
|
||||||
|
@ -93,5 +95,36 @@ namespace OpenTK.Platform.MacOS
|
||||||
}
|
}
|
||||||
|
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
|
#region IDisposable Members
|
||||||
|
|
||||||
|
void Dispose(bool manual)
|
||||||
|
{
|
||||||
|
if (!disposed)
|
||||||
|
{
|
||||||
|
if (manual)
|
||||||
|
{
|
||||||
|
InputDriver.Dispose();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Debug.Print("{0} leaked, did you forget to call Dispose()?", GetType());
|
||||||
|
}
|
||||||
|
disposed = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void Dispose()
|
||||||
|
{
|
||||||
|
Dispose(true);
|
||||||
|
GC.SuppressFinalize(this);
|
||||||
|
}
|
||||||
|
|
||||||
|
~MacOSFactory()
|
||||||
|
{
|
||||||
|
Dispose(false);
|
||||||
|
}
|
||||||
|
|
||||||
|
#endregion
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -34,6 +34,7 @@ namespace OpenTK.Platform.SDL2
|
||||||
class Sdl2Factory : IPlatformFactory
|
class Sdl2Factory : IPlatformFactory
|
||||||
{
|
{
|
||||||
readonly IInputDriver2 InputDriver = new Sdl2InputDriver();
|
readonly IInputDriver2 InputDriver = new Sdl2InputDriver();
|
||||||
|
bool disposed;
|
||||||
|
|
||||||
public Sdl2Factory()
|
public Sdl2Factory()
|
||||||
{
|
{
|
||||||
|
@ -102,6 +103,33 @@ namespace OpenTK.Platform.SDL2
|
||||||
}
|
}
|
||||||
|
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
|
#region IDisposable Members
|
||||||
|
|
||||||
|
void Dispose(bool manual)
|
||||||
|
{
|
||||||
|
if (!disposed)
|
||||||
|
{
|
||||||
|
if (manual)
|
||||||
|
{
|
||||||
|
InputDriver.Dispose();
|
||||||
|
}
|
||||||
|
disposed = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void Dispose()
|
||||||
|
{
|
||||||
|
Dispose(true);
|
||||||
|
GC.SuppressFinalize(this);
|
||||||
|
}
|
||||||
|
|
||||||
|
~Sdl2Factory()
|
||||||
|
{
|
||||||
|
Dispose(false);
|
||||||
|
}
|
||||||
|
|
||||||
|
#endregion
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -27,6 +27,7 @@
|
||||||
|
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
using System.Diagnostics;
|
||||||
using System.Runtime.InteropServices;
|
using System.Runtime.InteropServices;
|
||||||
using System.Threading;
|
using System.Threading;
|
||||||
using OpenTK.Input;
|
using OpenTK.Input;
|
||||||
|
@ -38,6 +39,7 @@ namespace OpenTK.Platform.SDL2
|
||||||
readonly Sdl2Keyboard keyboard_driver = new Sdl2Keyboard();
|
readonly Sdl2Keyboard keyboard_driver = new Sdl2Keyboard();
|
||||||
readonly Sdl2Mouse mouse_driver = new Sdl2Mouse();
|
readonly Sdl2Mouse mouse_driver = new Sdl2Mouse();
|
||||||
readonly SDL.SDL_EventFilter EventFilterDelegate;
|
readonly SDL.SDL_EventFilter EventFilterDelegate;
|
||||||
|
bool disposed;
|
||||||
|
|
||||||
public Sdl2InputDriver()
|
public Sdl2InputDriver()
|
||||||
{
|
{
|
||||||
|
@ -109,6 +111,37 @@ namespace OpenTK.Platform.SDL2
|
||||||
}
|
}
|
||||||
|
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
|
#region IDisposable Members
|
||||||
|
|
||||||
|
void Dispose(bool manual)
|
||||||
|
{
|
||||||
|
if (!disposed)
|
||||||
|
{
|
||||||
|
if (manual)
|
||||||
|
{
|
||||||
|
SDL.SDL_DelEventWatch(EventFilterDelegate, IntPtr.Zero);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Debug.WriteLine("Sdl2InputDriver leaked, did you forget to call Dispose()?");
|
||||||
|
}
|
||||||
|
disposed = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void Dispose()
|
||||||
|
{
|
||||||
|
Dispose(true);
|
||||||
|
GC.SuppressFinalize(this);
|
||||||
|
}
|
||||||
|
|
||||||
|
~Sdl2InputDriver()
|
||||||
|
{
|
||||||
|
Dispose(false);
|
||||||
|
}
|
||||||
|
|
||||||
|
#endregion
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -49,6 +49,7 @@ namespace OpenTK.Platform.SDL2
|
||||||
WindowState previous_window_state = WindowState.Normal;
|
WindowState previous_window_state = WindowState.Normal;
|
||||||
WindowBorder window_border = WindowBorder.Resizable;
|
WindowBorder window_border = WindowBorder.Resizable;
|
||||||
Icon icon;
|
Icon icon;
|
||||||
|
string window_title;
|
||||||
|
|
||||||
KeyboardDevice keyboard = new KeyboardDevice();
|
KeyboardDevice keyboard = new KeyboardDevice();
|
||||||
MouseDevice mouse = new MouseDevice();
|
MouseDevice mouse = new MouseDevice();
|
||||||
|
@ -84,6 +85,7 @@ namespace OpenTK.Platform.SDL2
|
||||||
window = new Sdl2WindowInfo(handle, null);
|
window = new Sdl2WindowInfo(handle, null);
|
||||||
window_id = SDL.SDL_GetWindowID(handle);
|
window_id = SDL.SDL_GetWindowID(handle);
|
||||||
windows.Add(window_id, this);
|
windows.Add(window_id, this);
|
||||||
|
window_title = title;
|
||||||
|
|
||||||
keyboard.Description = "Standard Windows keyboard";
|
keyboard.Description = "Standard Windows keyboard";
|
||||||
keyboard.NumberOfFunctionKeys = 12;
|
keyboard.NumberOfFunctionKeys = 12;
|
||||||
|
@ -227,6 +229,7 @@ namespace OpenTK.Platform.SDL2
|
||||||
{
|
{
|
||||||
exists = false;
|
exists = false;
|
||||||
|
|
||||||
|
SDL.SDL_DelEventWatch(EventFilterDelegate, IntPtr.Zero);
|
||||||
if (windows.ContainsKey(window_id))
|
if (windows.ContainsKey(window_id))
|
||||||
{
|
{
|
||||||
windows.Remove(window_id);
|
windows.Remove(window_id);
|
||||||
|
@ -245,10 +248,10 @@ namespace OpenTK.Platform.SDL2
|
||||||
SDL.SDL_SetRelativeMouseMode(
|
SDL.SDL_SetRelativeMouseMode(
|
||||||
grab ? SDL.SDL_bool.SDL_TRUE : SDL.SDL_bool.SDL_FALSE);
|
grab ? SDL.SDL_bool.SDL_TRUE : SDL.SDL_bool.SDL_FALSE);
|
||||||
|
|
||||||
if (grab)
|
//if (grab)
|
||||||
{
|
//{
|
||||||
mouse.Position = new Point(0, 0);
|
// mouse.Position = new Point(0, 0);
|
||||||
}
|
//}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Hack to force WindowState events to be pumped
|
// Hack to force WindowState events to be pumped
|
||||||
|
@ -458,6 +461,7 @@ namespace OpenTK.Platform.SDL2
|
||||||
set
|
set
|
||||||
{
|
{
|
||||||
SDL.SDL_SetWindowTitle(window.Handle, value);
|
SDL.SDL_SetWindowTitle(window.Handle, value);
|
||||||
|
window_title = value;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -49,10 +49,11 @@ namespace OpenTK.Platform.Windows
|
||||||
readonly object MouseLock = new object();
|
readonly object MouseLock = new object();
|
||||||
readonly object KeyboardLock = new object();
|
readonly object KeyboardLock = new object();
|
||||||
readonly WinMMJoystick gamepad_driver = new WinMMJoystick();
|
readonly WinMMJoystick gamepad_driver = new WinMMJoystick();
|
||||||
|
readonly WinKeyMap KeyMap = new WinKeyMap();
|
||||||
|
|
||||||
KeyboardState keyboard = new KeyboardState();
|
KeyboardState keyboard = new KeyboardState();
|
||||||
MouseState mouse = new MouseState();
|
MouseState mouse = new MouseState();
|
||||||
|
bool disposed;
|
||||||
readonly WinKeyMap KeyMap = new WinKeyMap();
|
|
||||||
|
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
|
@ -173,5 +174,36 @@ namespace OpenTK.Platform.Windows
|
||||||
}
|
}
|
||||||
|
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
|
#region IDisposable Members
|
||||||
|
|
||||||
|
void Dispose(bool manual)
|
||||||
|
{
|
||||||
|
if (!disposed)
|
||||||
|
{
|
||||||
|
if (manual)
|
||||||
|
{
|
||||||
|
// Todo: implement this
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Debug.Print("{0} leaked, did you forget to call Dispose()?", GetType());
|
||||||
|
}
|
||||||
|
disposed = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void Dispose()
|
||||||
|
{
|
||||||
|
Dispose(true);
|
||||||
|
GC.SuppressFinalize(this);
|
||||||
|
}
|
||||||
|
|
||||||
|
~WMInput()
|
||||||
|
{
|
||||||
|
Dispose(false);
|
||||||
|
}
|
||||||
|
|
||||||
|
#endregion
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -37,6 +37,7 @@ namespace OpenTK.Platform.Windows
|
||||||
|
|
||||||
class WinFactory : IPlatformFactory
|
class WinFactory : IPlatformFactory
|
||||||
{
|
{
|
||||||
|
bool disposed;
|
||||||
readonly object SyncRoot = new object();
|
readonly object SyncRoot = new object();
|
||||||
IInputDriver2 inputDriver;
|
IInputDriver2 inputDriver;
|
||||||
|
|
||||||
|
@ -123,5 +124,36 @@ namespace OpenTK.Platform.Windows
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#region IDisposable Members
|
||||||
|
|
||||||
|
void Dispose(bool manual)
|
||||||
|
{
|
||||||
|
if (!disposed)
|
||||||
|
{
|
||||||
|
if (manual)
|
||||||
|
{
|
||||||
|
InputDriver.Dispose();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Debug.Print("{0} leaked, did you forget to call Dispose()?", GetType());
|
||||||
|
}
|
||||||
|
disposed = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void Dispose()
|
||||||
|
{
|
||||||
|
Dispose(true);
|
||||||
|
GC.SuppressFinalize(this);
|
||||||
|
}
|
||||||
|
|
||||||
|
~WinFactory()
|
||||||
|
{
|
||||||
|
Dispose(false);
|
||||||
|
}
|
||||||
|
|
||||||
|
#endregion
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -33,6 +33,8 @@ namespace OpenTK.Platform.X11
|
||||||
{
|
{
|
||||||
class X11Factory : IPlatformFactory
|
class X11Factory : IPlatformFactory
|
||||||
{
|
{
|
||||||
|
bool disposed;
|
||||||
|
|
||||||
#region Constructors
|
#region Constructors
|
||||||
|
|
||||||
public X11Factory()
|
public X11Factory()
|
||||||
|
@ -97,5 +99,36 @@ namespace OpenTK.Platform.X11
|
||||||
}
|
}
|
||||||
|
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
|
#region IDisposable Members
|
||||||
|
|
||||||
|
void Dispose(bool manual)
|
||||||
|
{
|
||||||
|
if (!disposed)
|
||||||
|
{
|
||||||
|
if (manual)
|
||||||
|
{
|
||||||
|
// nothing to do
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Debug.Print("{0} leaked, did you forget to call Dispose()?", GetType());
|
||||||
|
}
|
||||||
|
disposed = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void Dispose()
|
||||||
|
{
|
||||||
|
Dispose(true);
|
||||||
|
GC.SuppressFinalize(this);
|
||||||
|
}
|
||||||
|
|
||||||
|
~X11Factory()
|
||||||
|
{
|
||||||
|
Dispose(false);
|
||||||
|
}
|
||||||
|
|
||||||
|
#endregion
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,79 +1,94 @@
|
||||||
#region License
|
#region License
|
||||||
//
|
//
|
||||||
// The Open Toolkit Library License
|
// The Open Toolkit Library License
|
||||||
//
|
//
|
||||||
// Copyright (c) 2006 - 2009 the Open Toolkit library.
|
// Copyright (c) 2006 - 2009 the Open Toolkit library.
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
// of this software and associated documentation files (the "Software"), to deal
|
// of this software and associated documentation files (the "Software"), to deal
|
||||||
// in the Software without restriction, including without limitation the rights to
|
// in the Software without restriction, including without limitation the rights to
|
||||||
// use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
|
// 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
|
// the Software, and to permit persons to whom the Software is furnished to do
|
||||||
// so, subject to the following conditions:
|
// so, subject to the following conditions:
|
||||||
//
|
//
|
||||||
// The above copyright notice and this permission notice shall be included in all
|
// The above copyright notice and this permission notice shall be included in all
|
||||||
// copies or substantial portions of the Software.
|
// copies or substantial portions of the Software.
|
||||||
//
|
//
|
||||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
||||||
// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
|
// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
|
||||||
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
||||||
// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
|
// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
|
||||||
// HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
// HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||||
// WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
// WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
|
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
|
||||||
// OTHER DEALINGS IN THE SOFTWARE.
|
// OTHER DEALINGS IN THE SOFTWARE.
|
||||||
//
|
//
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Text;
|
using System.Text;
|
||||||
|
using OpenTK.Platform;
|
||||||
namespace OpenTK
|
|
||||||
{
|
namespace OpenTK
|
||||||
/// <summary>
|
{
|
||||||
/// Provides static methods to manage an OpenTK application.
|
/// <summary>
|
||||||
/// </summary>
|
/// Provides static methods to manage an OpenTK application.
|
||||||
public sealed class Toolkit
|
/// </summary>
|
||||||
{
|
public sealed class Toolkit
|
||||||
volatile static bool initialized;
|
{
|
||||||
static readonly object InitLock = new object();
|
static Factory platform_factory;
|
||||||
|
|
||||||
#region Constructors
|
volatile static bool initialized;
|
||||||
|
static readonly object InitLock = new object();
|
||||||
Toolkit() { }
|
|
||||||
|
#region Constructors
|
||||||
#endregion
|
|
||||||
|
Toolkit() { }
|
||||||
#region Public Members
|
|
||||||
|
#endregion
|
||||||
/// <summary>
|
|
||||||
/// Initializes OpenTK. This method is necessary only if you are using OpenTK
|
#region Public Members
|
||||||
/// alongside a different windowing toolkit (e.g. GTK#) and should be the very
|
|
||||||
/// first method called by your application (i.e. calling this method should be
|
/// <summary>
|
||||||
/// the very first statement executed by the "Main" method).
|
/// Initializes OpenTK. This method is necessary only if you are using OpenTK
|
||||||
/// </summary>
|
/// alongside a different windowing toolkit (e.g. GTK#) and should be the very
|
||||||
/// <remarks>
|
/// first method called by your application (i.e. calling this method should be
|
||||||
/// Some windowing toolkits do not configure the underlying platform
|
/// the very first statement executed by the "Main" method).
|
||||||
/// correctly or configure it in a way that is incompatible with OpenTK.
|
/// </summary>
|
||||||
/// Calling this method first ensures that OpenTK is given the chance to
|
/// <remarks>
|
||||||
/// initialize itself and configure the platform correctly.
|
/// Some windowing toolkits do not configure the underlying platform
|
||||||
/// </remarks>
|
/// correctly or configure it in a way that is incompatible with OpenTK.
|
||||||
public static void Init()
|
/// Calling this method first ensures that OpenTK is given the chance to
|
||||||
{
|
/// initialize itself and configure the platform correctly.
|
||||||
lock (InitLock)
|
/// </remarks>
|
||||||
{
|
public static IDisposable Init()
|
||||||
if (!initialized)
|
{
|
||||||
{
|
lock (InitLock)
|
||||||
initialized = true;
|
{
|
||||||
Configuration.Init();
|
if (!initialized)
|
||||||
// The actual initialization takes place in the platform-specific factory
|
{
|
||||||
// constructors.
|
initialized = true;
|
||||||
new Platform.Factory();
|
Configuration.Init();
|
||||||
}
|
// The actual initialization takes place in the platform-specific factory
|
||||||
}
|
// constructors.
|
||||||
}
|
platform_factory = new Platform.Factory();
|
||||||
|
AppDomain.CurrentDomain.DomainUnload += Deinit;
|
||||||
#endregion
|
}
|
||||||
}
|
return platform_factory;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#endregion
|
||||||
|
|
||||||
|
#region Private Members
|
||||||
|
|
||||||
|
static void Deinit(object sender, EventArgs e)
|
||||||
|
{
|
||||||
|
AppDomain.CurrentDomain.DomainUnload -= Deinit;
|
||||||
|
platform_factory.Dispose();
|
||||||
|
}
|
||||||
|
|
||||||
|
#endregion
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
Loading…
Reference in a new issue