/// <summary> /// Releases resources associated with the object. /// </summary> /// <param name="disposing">true if the object is being disposed; false if the object is being finalized.</param> protected override void Dispose(Boolean disposing) { if (Disposed) { return; } if (samplerObjects != null) { for (int i = 0; i < samplerObjects.Length; i++) { SafeDispose.Dispose(samplerObjects[i]); } } if (gl.Initialized) { gl.Uninitialize(); } OpenGLEnvironment.DeleteOpenGLContext(context); context = IntPtr.Zero; SafeDispose.Dispose(OpenGLEnvironment); base.Dispose(disposing); }
/// <summary> /// Sets the OpenGL environment attributes which correspond to the application's OpenGL settings. /// </summary> private void InitOpenGLEnvironment(OpenGLGraphicsConfiguration configuration, Boolean isGLES) { if (!OpenGLEnvironment.RequestOpenGLProfile(isGLES)) { OpenGLEnvironment.ThrowPlatformErrorException(); } if (!OpenGLEnvironment.RequestDepthSize(configuration.BackBufferDepthSize)) { OpenGLEnvironment.ThrowPlatformErrorException(); } if (!OpenGLEnvironment.RequestStencilSize(configuration.BackBufferStencilSize)) { OpenGLEnvironment.ThrowPlatformErrorException(); } if (configuration.Use32BitFramebuffer) { if (!OpenGLEnvironment.Request32BitFramebuffer()) { OpenGLEnvironment.ThrowPlatformErrorException(); } } else { if (!OpenGLEnvironment.Request24BitFramebuffer()) { OpenGLEnvironment.ThrowPlatformErrorException(); } } if (configuration.SrgbBuffersEnabled) { if (!OpenGLEnvironment.RequestSrgbCapableFramebuffer()) { OpenGLEnvironment.ThrowPlatformErrorException(); } if (!OpenGLEnvironment.IsFramebufferSrgbCapable) { configuration.SrgbBuffersEnabled = false; } } }
/// <summary> /// Attempts to create an OpenGL context. /// </summary> private static IntPtr?TryCreateOpenGLContext(UltravioletContext uv, OpenGLEnvironment environment, Version versionRequested, Version versionRequired, Boolean debug, Boolean throwOnFailure) { if (!environment.RequestDebugContext(debug)) { environment.ThrowPlatformErrorException(); } var gles = (uv.Platform == UltravioletPlatform.Android || uv.Platform == UltravioletPlatform.iOS); var versionArray = gles ? KnownOpenGLESVersions : KnownOpenGLVersions; var versionMin = versionRequested ?? versionRequired; var versionCurrent = versionRequested ?? versionArray[0]; var versionCurrentIndex = Array.IndexOf(versionArray, versionCurrent); IntPtr context; do { if (versionCurrent < versionMin) { if (throwOnFailure) { throw new InvalidOperationException(OpenGLStrings.DoesNotMeetMinimumVersionRequirement.Format(versionMin.Major, versionMin.Minor)); } return(null); } if (!environment.RequestOpenGLVersion(versionCurrent)) { environment.ThrowPlatformErrorException(); } versionCurrent = versionArray[++versionCurrentIndex]; }while ((context = environment.CreateOpenGLContext()) == IntPtr.Zero); return(context); }
/// <summary> /// Initializes a new instance of the <see cref="OpenGLInitializer"/> class. /// </summary> /// <param name="environment">The interface with which OpenGL communicates with its underlying platform environment.</param> public OpenGLInitializer(OpenGLEnvironment environment) { Contract.Require(environment, nameof(environment)); this.environment = environment; }
/// <summary> /// Initializes a new instance of the OpenGLUltravioletGraphics class. /// </summary> /// <param name="uv">The Ultraviolet context.</param> /// <param name="configuration">The Ultraviolet Framework configuration settings for the current context.</param> public unsafe OpenGLUltravioletGraphics(UltravioletContext uv, UltravioletConfiguration configuration) : base(uv) { var glGraphicsConfiguration = configuration.GraphicsConfiguration as OpenGLGraphicsConfiguration; if (glGraphicsConfiguration == null) { throw new InvalidOperationException(OpenGLStrings.InvalidGraphicsConfiguration); } this.OpenGLEnvironment = uv.GetFactoryMethod <OpenGLEnvironmentFactory>()(uv); InitOpenGLVersion(glGraphicsConfiguration, out var versionRequested, out var versionRequired, out var isGLES); InitOpenGLEnvironment(glGraphicsConfiguration, isGLES); uv.GetPlatform().InitializePrimaryWindow(configuration); if (this.context == IntPtr.Zero && configuration.Debug) { this.context = TryCreateOpenGLContext(uv, OpenGLEnvironment, versionRequested, versionRequired, true, false) ?? IntPtr.Zero; } if (this.context == IntPtr.Zero) { this.context = TryCreateOpenGLContext(uv, OpenGLEnvironment, versionRequested, versionRequired, false, true) ?? IntPtr.Zero; } if (!OpenGLEnvironment.SetSwapInterval(1) && uv.Platform != UltravioletPlatform.iOS) { OpenGLEnvironment.ThrowPlatformErrorException(); } if (gl.Initialized) { gl.Uninitialize(); } gl.Initialize(new OpenGLInitializer(OpenGLEnvironment)); if (!gl.IsVersionAtLeast(versionRequested ?? versionRequired)) { throw new InvalidOperationException(OpenGLStrings.DoesNotMeetMinimumVersionRequirement.Format(gl.MajorVersion, gl.MinorVersion, versionRequested.Major, versionRequested.Minor)); } OpenGLState.ResetCache(); if (!VerifyCapabilities()) { throw new NotSupportedException(OpenGLStrings.UnsupportedGraphicsDevice); } if (configuration.Debug && configuration.DebugCallback != null) { InitializeDebugOutput(configuration); } this.Capabilities = new OpenGLGraphicsCapabilities(configuration); if (Capabilities.SrgbEncodingEnabled && gl.IsFramebufferSrgbAvailable) { gl.Enable(gl.GL_FRAMEBUFFER_SRGB); gl.ThrowIfError(); } this.maxTextureStages = gl.GetInteger(gl.GL_MAX_TEXTURE_IMAGE_UNITS); this.textures = new Texture[maxTextureStages]; this.samplerStates = new SamplerState[maxTextureStages]; this.samplerObjects = Capabilities.SupportsIndependentSamplerState ? new OpenGLSamplerObject[maxTextureStages] : null; this.backBufferRenderTargetUsage = glGraphicsConfiguration.BackBufferRenderTargetUsage; if (samplerObjects != null) { for (int i = 0; i < samplerObjects.Length; i++) { samplerObjects[i] = new OpenGLSamplerObject(Ultraviolet); samplerObjects[i].Bind((uint)i); } } OpenGLState.VerifyCache(); ResetDeviceStates(); }