protected override void Dispose(bool disposing) { if (IsDisposed || ContextHandle == IntPtr.Zero) { return; } Debug.Print("Disposing of AGL context."); Agl.aglSetCurrentContext(IntPtr.Zero); //Debug.Print("Setting drawable to null for context {0}.", Handle.Handle); //Agl.aglSetDrawable(Handle.Handle, IntPtr.Zero); // I do not know MacOS allows us to destroy a context from a separate thread, // like the finalizer thread. It's untested, but worst case is probably // an exception on application exit, which would be logged to the console. Debug.Print("Destroying context"); byte code = Agl.aglDestroyContext(ContextHandle); try { Agl.CheckReturnValue(code, "aglDestroyContext"); ContextHandle = IntPtr.Zero; Debug.Print("Context destruction completed successfully."); } catch (MacOSException) { Debug.Print("Failed to destroy context."); if (disposing) { throw; } } IsDisposed = true; }
private void AddPixelAttrib(List<int> aglAttributes, Agl.PixelFormatAttribute pixelFormatAttribute, int value) { Debug.Print("{0} : {1}", pixelFormatAttribute, value); aglAttributes.Add((int)pixelFormatAttribute); aglAttributes.Add(value); }
public override void Update(IWindowInfo window) { CarbonWindowInfo carbonWindow1 = (CarbonWindowInfo)window; if (carbonWindow1.GoFullScreenHack) { carbonWindow1.GoFullScreenHack = false; CarbonGLNative carbonWindow2 = this.GetCarbonWindow(carbonWindow1); if (carbonWindow2 == null) { return; } carbonWindow2.SetFullscreen(this); } else { if (carbonWindow1.GoWindowedHack) { carbonWindow1.GoWindowedHack = false; CarbonGLNative carbonWindow2 = this.GetCarbonWindow(carbonWindow1); if (carbonWindow2 != null) { carbonWindow2.UnsetFullscreen(this); } } if (this.mIsFullscreen) { return; } this.SetDrawable(carbonWindow1); this.SetBufferRect(carbonWindow1); int num = (int)Agl.aglUpdateContext(this.Handle.Handle); } }
void SetBufferRect(CarbonWindowInfo carbonWindow) { if (carbonWindow.IsControl == false) { return; } System.Windows.Forms.Control ctrl = Control.FromHandle(carbonWindow.WindowRef); if (ctrl.TopLevelControl == null) { return; } Rect rect = API.GetControlBounds(carbonWindow.WindowRef); System.Windows.Forms.Form frm = (System.Windows.Forms.Form)ctrl.TopLevelControl; System.Drawing.Point loc = frm.PointToClient(ctrl.PointToScreen(System.Drawing.Point.Empty)); rect.X = (short)loc.X; rect.Y = (short)loc.Y; Debug.Print("Setting buffer_rect for control."); Debug.Print("MacOS Coordinate Rect: {0}", rect); rect.Y = (short)(ctrl.TopLevelControl.ClientSize.Height - rect.Y - rect.Height); Debug.Print(" AGL Coordinate Rect: {0}", rect); int[] glrect = new int[4]; glrect[0] = rect.X; glrect[1] = rect.Y; glrect[2] = rect.Width; glrect[3] = rect.Height; Agl.aglSetInteger(Handle.Handle, Agl.ParameterNames.AGL_BUFFER_RECT, glrect); MyAGLReportError("aglSetInteger"); Agl.aglEnable(Handle.Handle, Agl.ParameterNames.AGL_BUFFER_RECT); MyAGLReportError("aglEnable"); }
public void Update(IWindowInfo window) { SetDrawable(window); SetBufferRect(window); Agl.aglUpdateContext(Context.Handle); }
private void SetBufferRect(IWindowInfo carbonWindow) { Rect rect = API.GetControlBounds(carbonWindow.Handle); Debug.Print("Setting buffer_rect for control."); Debug.Print("MacOS Coordinate Rect: {0}", rect); int[] glrect = new int[4]; if (XOffset != null) { glrect[0] = rect.X + XOffset(); } else { glrect[0] = rect.X; } if (YOffset != null) { glrect[1] = rect.Y + YOffset(); } else { glrect[1] = rect.Y; } glrect[2] = rect.Width; glrect[3] = rect.Height; Agl.aglSetInteger(Context.Handle, Agl.ParameterNames.AGL_BUFFER_RECT, glrect); MyAGLReportError("aglSetInteger"); Agl.aglEnable(Context.Handle, Agl.ParameterNames.AGL_BUFFER_RECT); MyAGLReportError("aglEnable"); }
void Dispose(bool disposing) { if (IsDisposed || Handle.Handle == IntPtr.Zero) { return; } Debug.Print("Disposing of AGL context."); Agl.aglSetCurrentContext(IntPtr.Zero); //Debug.Print("Setting drawable to null for context {0}.", Handle.Handle); //Agl.aglSetDrawable(Handle.Handle, IntPtr.Zero); // I do not know MacOS allows us to destroy a context from a separate thread, // like the finalizer thread. It's untested, but worst case is probably // an exception on application exit, which would be logged to the console. Debug.Print("Destroying context"); if (Agl.aglDestroyContext(Handle.Handle) == true) { Debug.Print("Context destruction completed successfully."); Handle = ContextHandle.Zero; return; } // failed to destroy context. Debug.WriteLine("Failed to destroy context."); Debug.WriteLine(Agl.ErrorString(Agl.GetError())); // don't throw an exception from the finalizer thread. if (disposing) { throw new MacOSException((OSStatus)Agl.GetError(), Agl.ErrorString(Agl.GetError())); } IsDisposed = true; }
private GraphicsMode GetGraphicsModeFromPixelFormat(IntPtr pixelformat) { int r, g, b, a; Agl.aglDescribePixelFormat(pixelformat, Agl.PixelFormatAttribute.AGL_RED_SIZE, out r); Agl.aglDescribePixelFormat(pixelformat, Agl.PixelFormatAttribute.AGL_GREEN_SIZE, out g); Agl.aglDescribePixelFormat(pixelformat, Agl.PixelFormatAttribute.AGL_BLUE_SIZE, out b); Agl.aglDescribePixelFormat(pixelformat, Agl.PixelFormatAttribute.AGL_ALPHA_SIZE, out a); int ar, ag, ab, aa; Agl.aglDescribePixelFormat(pixelformat, Agl.PixelFormatAttribute.AGL_ACCUM_ALPHA_SIZE, out aa); Agl.aglDescribePixelFormat(pixelformat, Agl.PixelFormatAttribute.AGL_ACCUM_RED_SIZE, out ar); Agl.aglDescribePixelFormat(pixelformat, Agl.PixelFormatAttribute.AGL_ACCUM_GREEN_SIZE, out ag); Agl.aglDescribePixelFormat(pixelformat, Agl.PixelFormatAttribute.AGL_ACCUM_BLUE_SIZE, out ab); int depth, stencil, samples, buffers, stereo; Agl.aglDescribePixelFormat(pixelformat, Agl.PixelFormatAttribute.AGL_DEPTH_SIZE, out depth); Agl.aglDescribePixelFormat(pixelformat, Agl.PixelFormatAttribute.AGL_STENCIL_SIZE, out stencil); Agl.aglDescribePixelFormat(pixelformat, Agl.PixelFormatAttribute.AGL_SAMPLES_ARB, out samples); Agl.aglDescribePixelFormat(pixelformat, Agl.PixelFormatAttribute.AGL_DOUBLEBUFFER, out buffers); Agl.aglDescribePixelFormat(pixelformat, Agl.PixelFormatAttribute.AGL_STEREO, out stereo); return(new GraphicsMode(new ColorFormat(r, g, b, a), depth, stencil, samples, new ColorFormat(ar, ag, ab, aa), buffers + 1, stereo != 0)); }
internal void SetFullScreen(CarbonWindowInfo info, out int width, out int height) { CarbonGLNative wind = GetCarbonWindow(info); Debug.Print("Switching to full screen {0}x{1} on context {2}", wind.TargetDisplayDevice.Width, wind.TargetDisplayDevice.Height, Handle.Handle); CG.DisplayCapture(GetQuartzDevice(info)); Agl.aglSetFullScreen(Handle.Handle, wind.TargetDisplayDevice.Width, wind.TargetDisplayDevice.Height, 0, 0); MakeCurrent(info); width = wind.TargetDisplayDevice.Width; height = wind.TargetDisplayDevice.Height; // This is a weird hack to workaround a bug where the first time a context // is made fullscreen, we just end up with a blank screen. So we undo it as fullscreen // and redo it as fullscreen. if (firstFullScreen == false) { firstFullScreen = true; UnsetFullScreen(info); SetFullScreen(info, out width, out height); } mIsFullscreen = true; }
public GraphicsMode SelectGraphicsMode(ColorFormat color, int depth, int stencil, int samples, ColorFormat accum, int buffers, bool stereo) { IntPtr pixelformat; do { pixelformat = SelectPixelFormat( color, depth, stencil, samples, accum, buffers, stereo, true, Device); Agl.AglError err = Agl.GetError(); if (pixelformat == IntPtr.Zero || err == Agl.AglError.BadPixelFormat) { Debug.Print("Failed to create full screen pixel format."); Debug.Print("Trying again to create a non-fullscreen pixel format."); pixelformat = SelectPixelFormat( color, depth, stencil, samples, accum, buffers, stereo, false, IntPtr.Zero); } if (pixelformat == IntPtr.Zero) { if (!Utilities.RelaxGraphicsMode( ref color, ref depth, ref stencil, ref samples, ref accum, ref buffers, ref stereo)) { throw new GraphicsModeException("Requested GraphicsMode not available."); } } }while (pixelformat == IntPtr.Zero); return(GetGraphicsModeFromPixelFormat(pixelformat)); }
public override void MakeCurrent(IWindowInfo window) { if (Agl.aglSetCurrentContext(Handle.Handle) == false) { MyAGLReportError("aglSetCurrentContext"); } }
internal void SetFullScreen(CarbonWindow wind, out int width, out int height) { int displayWidth = wind.Display.Bounds.Width; int displayHeight = wind.Display.Bounds.Height; Debug.Print("Switching to full screen {0}x{1} on context {2}", displayWidth, displayHeight, ContextHandle); CG.CGDisplayCapture(CG.CGMainDisplayID()); byte code = Agl.aglSetFullScreen(ContextHandle, displayWidth, displayHeight, 0, 0); Agl.CheckReturnValue(code, "aglSetFullScreen"); MakeCurrent(wind); width = displayWidth; height = displayHeight; // This is a weird hack to workaround a bug where the first time a context // is made fullscreen, we just end up with a blank screen. So we undo it as fullscreen // and redo it as fullscreen. if (!firstFullScreen) { firstFullScreen = true; UnsetFullScreen(wind); SetFullScreen(wind, out width, out height); } mIsFullscreen = true; }
public virtual GraphicsContext.GetCurrentContextDelegate CreateGetCurrentGraphicsContext() { return((GraphicsContext.GetCurrentContextDelegate) delegate { return new ContextHandle(Agl.aglGetCurrentContext()); }); }
private void SetDrawable(IWindowInfo carbonWindow) { IntPtr windowPort = GetWindowPortForWindowInfo(carbonWindow); //Debug.Print("Setting drawable for context {0} to window port: {1}", Handle.Handle, windowPort); Agl.aglSetDrawable(Context.Handle, windowPort); MyAGLReportError("aglSetDrawable"); }
void SetDrawable(CarbonWindowInfo carbonWindow) { IntPtr windowPort = GetWindowPortForWindowInfo(carbonWindow); Agl.aglSetDrawable(Handle.Handle, windowPort); MyAGLReportError("aglSetDrawable"); }
private void MyAGLReportError(string function) { Agl.AglError error = Agl.GetError(); if (error != Agl.AglError.NoError) { throw new MacOSException((OSStatus)error, string.Format("AGL Error from function {0}: {1} {2}", (object)function, (object)error, (object)Agl.ErrorString(error))); } }
public override void MakeCurrent(IWindowInfo window) { if (Agl.aglSetCurrentContext(this.Handle.Handle)) { return; } this.MyAGLReportError("aglSetCurrentContext"); }
internal static void aglSetDrawable(IntPtr ctx, IntPtr draw) { if ((int)Agl._aglSetDrawable(ctx, draw) != 0) { return; } Agl.AglError error = Agl.GetError(); throw new MacOSException(error, Agl.ErrorString(error)); }
internal static void aglSetFullScreen(IntPtr ctx, int width, int height, int freq, int device) { if ((int)Agl._aglSetFullScreen(ctx, width, height, freq, device) != 0) { return; } Agl.AglError error = Agl.GetError(); throw new MacOSException(error, Agl.ErrorString(error)); }
public override void Update(IWindowInfo window) { CarbonWindowInfo carbonWindow = (CarbonWindowInfo)window; SetDrawable(carbonWindow); SetBufferRect(carbonWindow); Agl.aglUpdateContext(Handle.Handle); }
internal void UnsetFullScreen(CarbonWindowInfo windowInfo) { Agl.aglSetDrawable(this.Handle.Handle, IntPtr.Zero); int num1 = (int)Agl.aglUpdateContext(this.Handle.Handle); int num2 = (int)CG.DisplayRelease(this.GetQuartzDevice(windowInfo)); this.SetDrawable(windowInfo); this.mIsFullscreen = false; }
void SetDrawable(CarbonWindow window) { IntPtr windowPort = API.GetWindowPort(window.WinHandle); //Debug.Print("Setting drawable for context {0} to window port: {1}", Handle.Handle, windowPort); byte code = Agl.aglSetDrawable(ContextHandle, windowPort); Agl.CheckReturnValue(code, "aglSetDrawable"); }
internal void UnsetFullScreen(CarbonWindowInfo windowInfo) { Debug.Print("Unsetting AGL fullscreen."); Agl.aglSetDrawable(Handle.Handle, IntPtr.Zero); Agl.aglUpdateContext(Handle.Handle); CG.DisplayRelease(GetQuartzDevice(windowInfo)); Debug.Print("Resetting drawable."); SetDrawable(windowInfo); mIsFullscreen = false; }
private void MyAGLReportError(string function) { Agl.AglError err = Agl.GetError(); if (err != Agl.AglError.NoError) { throw new Exception(String.Format( "AGL Error from function {0}: {1} {2}", function, err, Agl.ErrorString(err))); } }
public override void SwapBuffers() { if (!this.firstSwap && this.carbonWindow.IsControl) { this.firstSwap = true; this.SetDrawable(this.carbonWindow); this.Update((IWindowInfo)this.carbonWindow); } Agl.aglSwapBuffers(this.Handle.Handle); this.MyAGLReportError("aglSwapBuffers"); }
void CreateContext(GraphicsMode mode, CarbonWindow wind, bool fullscreen) { int[] attribs = GetAttribs(mode, fullscreen); IntPtr pixelFormat; // Choose a pixel format with the attributes we specified. if (fullscreen) { IntPtr gdevice; IntPtr display = CG.CGMainDisplayID(); OSStatus status = API.DMGetGDeviceByDisplayID(display, out gdevice, false); if (status != OSStatus.NoError) { throw new MacOSException(status, "DMGetGDeviceByDisplayID failed."); } pixelFormat = Agl.aglChoosePixelFormat(ref gdevice, 1, attribs); int err = Agl.aglGetError(); if (err == Agl.AGL_BAD_PIXEL_FORMAT) { Debug.Print("Failed to create full screen pixel format."); Debug.Print("Trying again to create a non-fullscreen pixel format."); CreateContext(mode, wind, false); return; } } else { pixelFormat = Agl.aglChoosePixelFormat(IntPtr.Zero, 0, attribs); Agl.CheckReturnValue(0, "aglChoosePixelFormat"); } Debug.Print("Creating AGL context."); // create the context and share it with the share reference. ContextHandle = Agl.aglCreateContext(pixelFormat, IntPtr.Zero); Agl.CheckReturnValue(0, "aglCreateContext"); // Free the pixel format from memory. Agl.aglDestroyPixelFormat(pixelFormat); Agl.CheckReturnValue(0, "aglDestroyPixelFormat"); SetDrawable(wind); Update(wind); MakeCurrent(wind); Debug.Print("context: {0}", ContextHandle); }
internal void SetFullScreen(CarbonWindowInfo info) { Agl.aglSetFullScreen(Handle.Handle, 0, 0, 0, 0); // This is a weird hack to workaround a bug where the first time a context // is made fullscreen, we just end up with a blank screen. So we undo it as fullscreen // and redo it as fullscreen. if (firstFullScreen == false) { firstFullScreen = true; UnsetFullScreen(info); SetFullScreen(info); } }
void CreateContext(GraphicsMode mode, CarbonWindowInfo carbonWindow, IntPtr shareContextRef, bool fullscreen) { Debug.Print("AGL pixel format attributes:"); AGLPixelFormat myAGLPixelFormat; // Choose a pixel format with the attributes we specified. IntPtr gdevice; IntPtr cgdevice = GetQuartzDevice(carbonWindow); if (cgdevice == IntPtr.Zero) { cgdevice = (IntPtr)DisplayDevice.Default.Id; } OSStatus status = Carbon.API.DMGetGDeviceByDisplayID(cgdevice, out gdevice, false); if (status != OSStatus.NoError) { throw new MacOSException(status, "DMGetGDeviceByDisplayID failed."); } IGraphicsMode selector = new MacOSGraphicsMode(gdevice); Mode = selector.SelectGraphicsMode( mode.ColorFormat, mode.Depth, mode.Stencil, mode.Samples, mode.AccumulatorFormat, mode.Buffers, mode.Stereo); MyAGLReportError("aglChoosePixelFormat"); Debug.Print("Creating AGL context. Sharing with {0}", shareContextRef); myAGLPixelFormat = Mode.Index.Value; // create the context and share it with the share reference. Handle = new ContextHandle(Agl.aglCreateContext(myAGLPixelFormat, shareContextRef)); MyAGLReportError("aglCreateContext"); // Free the pixel format from memory. Agl.aglDestroyPixelFormat(myAGLPixelFormat); MyAGLReportError("aglDestroyPixelFormat"); Debug.Print("IsControl: {0}", carbonWindow.IsControl); SetDrawable(carbonWindow); SetBufferRect(carbonWindow); Update(carbonWindow); MakeCurrent(carbonWindow); Debug.Print("context: {0}", Handle.Handle); }
public override void SwapBuffers() { // this is part of the hack to avoid dropping the first frame when // using multiple GLControls. if (firstSwap == false && carbonWindow.IsControl) { Debug.WriteLine("--> Resetting drawable. <--"); firstSwap = true; SetDrawable(carbonWindow); Update(carbonWindow); } Agl.aglSwapBuffers(Handle.Handle); MyAGLReportError("aglSwapBuffers"); }
internal void UnsetFullScreen(CarbonWindow window) { Debug.Print("Unsetting AGL fullscreen."); byte code = Agl.aglSetDrawable(ContextHandle, IntPtr.Zero); Agl.CheckReturnValue(code, "aglSetDrawable"); code = Agl.aglUpdateContext(ContextHandle); Agl.CheckReturnValue(code, "aglUpdateContext"); CG.CGDisplayRelease(CG.CGMainDisplayID()); Debug.Print("Resetting drawable."); SetDrawable(window); mIsFullscreen = false; }
public override void Update(IWindowInfo window) { CarbonWindowInfo carbonWindow = (CarbonWindowInfo)window; if (carbonWindow.GoFullScreenHack) { carbonWindow.GoFullScreenHack = false; CarbonGLNative wind = GetCarbonWindow(carbonWindow); if (wind != null) { wind.SetFullscreen(this); } else { Debug.Print("Could not find window!"); } return; } else if (carbonWindow.GoWindowedHack) { carbonWindow.GoWindowedHack = false; CarbonGLNative wind = GetCarbonWindow(carbonWindow); if (wind != null) { wind.UnsetFullscreen(this); } else { Debug.Print("Could not find window!"); } } if (mIsFullscreen) { return; } SetDrawable(carbonWindow); SetBufferRect(carbonWindow); Agl.aglUpdateContext(Handle.Handle); }
internal static bool aglSetInteger(IntPtr ctx, Agl.ParameterNames pname, int[] @params);
private void AddPixelAttrib(List<int> attribs, Agl.PixelFormatAttribute name, int value) { attribs.Add((int)name); attribs.Add(value); }
private void AddPixelAttrib(List<int> aglAttributes, Agl.PixelFormatAttribute pixelFormatAttribute, int value) { aglAttributes.Add((int) pixelFormatAttribute); aglAttributes.Add(value); }
internal MacOSException(Agl.AglError errorCode, string message) : base(message) { this.errorCode = (OSStatus)errorCode; }
private static IntPtr _aglErrorString(Agl.AglError code);
private void AddPixelAttrib(List<int> aglAttributes, Agl.PixelFormatAttribute pixelFormatAttribute) { Debug.Print(pixelFormatAttribute.ToString()); aglAttributes.Add((int)pixelFormatAttribute); }
internal static bool aglSetInteger(IntPtr ctx, Agl.ParameterNames pname, ref int param);
internal static bool aglGetInteger(IntPtr ctx, Agl.ParameterNames pname, out int param);
internal static bool aglDescribePixelFormat(IntPtr pix, Agl.PixelFormatAttribute attrib, out int value);
internal static bool aglEnable(IntPtr ctx, Agl.ParameterNames pname);
internal static string ErrorString(Agl.AglError code) { return Marshal.PtrToStringAnsi(Agl._aglErrorString(code)); }