From e5a386ccdff0a6dee27e55bbeff1fd885d6dcecd Mon Sep 17 00:00:00 2001 From: Kirill Chibisov Date: Tue, 12 Nov 2024 16:59:35 +0300 Subject: [PATCH 1/4] api/context: unify surfaceless APIs on context The API was implemented by all backend, this patch simply promotes it to the top-level trait. --- CHANGELOG.md | 11 +------- glutin/src/api/cgl/context.rs | 23 +++++++---------- glutin/src/api/egl/context.rs | 23 +++++++---------- glutin/src/api/glx/context.rs | 27 +++++++------------- glutin/src/api/wgl/context.rs | 27 +++++++------------- glutin/src/context.rs | 47 ++++++++++++++++++++++++++++------- 6 files changed, 75 insertions(+), 83 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index c4428df67e..e83b252dcb 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,17 +1,8 @@ # Unreleased - Added `PossiblyCurrentContext::make_not_current_in_place(&self)` for when `Send` capability of `NotCurrentContext` is not required. -- Added `NotCurrentContext::make_current_surfaceless(self)` and - `PossiblyCurrentContext::make_current_surfaceless(&self)` in the `Cgl` - implementation to allow the use of surfaceless contexts on MacOS. -- Added `NotCurrentContext::make_current_surfaceless(self)` and - `PossiblyCurrentContext::make_current_surfaceless(&self)` in the `Glx` - implementation to allow the use of surfaceless contexts with GLX. -- Added `NotCurrentContext::make_current_surfaceless(self)` and - `PossiblyCurrentContext::make_current_surfaceless(&self)` in the `Wgl` - implementation to allow the use of surfaceless contexts with WGL. - Added workaround for EGL drivers reporting `EGL_KHR_platform_gbm` without EGL 1.5 client. - +- **Breaking:** Added `make_current_surfaceless(self)` for `{Possibly,Not}CurrentGlContext`. # Version 0.32.1 diff --git a/glutin/src/api/cgl/context.rs b/glutin/src/api/cgl/context.rs index 8450286709..2d6f3516e7 100644 --- a/glutin/src/api/cgl/context.rs +++ b/glutin/src/api/cgl/context.rs @@ -74,13 +74,6 @@ pub struct NotCurrentContext { } impl NotCurrentContext { - /// Make a [`Self::PossiblyCurrentContext`] indicating that the context - /// could be current on the thread. - pub fn make_current_surfaceless(self) -> Result { - self.inner.make_current_surfaceless()?; - Ok(PossiblyCurrentContext { inner: self.inner, _nosendsync: PhantomData }) - } - fn new(inner: ContextInner) -> Self { Self { inner, _nosync: PhantomData } } @@ -109,6 +102,11 @@ impl NotCurrentGlContext for NotCurrentContext { ) -> Result { Err(self.inner.make_current_draw_read(surface_draw, surface_read).into()) } + + fn make_current_surfaceless(self) -> Result { + self.inner.make_current_surfaceless()?; + Ok(PossiblyCurrentContext { inner: self.inner, _nosendsync: PhantomData }) + } } impl GlContext for NotCurrentContext { @@ -150,13 +148,6 @@ pub struct PossiblyCurrentContext { _nosendsync: PhantomData<*mut ()>, } -impl PossiblyCurrentContext { - /// Make this context current on the calling thread. - pub fn make_current_surfaceless(&self) -> Result<()> { - self.inner.make_current_surfaceless() - } -} - impl PossiblyCurrentGlContext for PossiblyCurrentContext { type NotCurrentContext = NotCurrentContext; type Surface = Surface; @@ -189,6 +180,10 @@ impl PossiblyCurrentGlContext for PossiblyCurrentContext { ) -> Result<()> { Err(self.inner.make_current_draw_read(surface_draw, surface_read).into()) } + + fn make_current_surfaceless(&self) -> Result<()> { + self.inner.make_current_surfaceless() + } } impl GlContext for PossiblyCurrentContext { diff --git a/glutin/src/api/egl/context.rs b/glutin/src/api/egl/context.rs index d8827d9329..b58b1cbf9e 100644 --- a/glutin/src/api/egl/context.rs +++ b/glutin/src/api/egl/context.rs @@ -172,13 +172,6 @@ pub struct NotCurrentContext { } impl NotCurrentContext { - /// Make a [`Self::PossiblyCurrentContext`] indicating that the context - /// could be current on the thread. - pub fn make_current_surfaceless(self) -> Result { - self.inner.make_current_surfaceless()?; - Ok(PossiblyCurrentContext { inner: self.inner, _nosendsync: PhantomData }) - } - fn new(inner: ContextInner) -> Self { Self { inner } } @@ -208,6 +201,11 @@ impl NotCurrentGlContext for NotCurrentContext { self.inner.make_current_draw_read(surface_draw, surface_read)?; Ok(PossiblyCurrentContext { inner: self.inner, _nosendsync: PhantomData }) } + + fn make_current_surfaceless(self) -> Result { + self.inner.make_current_surfaceless()?; + Ok(PossiblyCurrentContext { inner: self.inner, _nosendsync: PhantomData }) + } } impl GlContext for NotCurrentContext { @@ -247,13 +245,6 @@ pub struct PossiblyCurrentContext { _nosendsync: PhantomData, } -impl PossiblyCurrentContext { - /// Make this context current on the calling thread. - pub fn make_current_surfaceless(&self) -> Result<()> { - self.inner.make_current_surfaceless() - } -} - impl PossiblyCurrentGlContext for PossiblyCurrentContext { type NotCurrentContext = NotCurrentContext; type Surface = Surface; @@ -285,6 +276,10 @@ impl PossiblyCurrentGlContext for PossiblyCurrentContext { ) -> Result<()> { self.inner.make_current_draw_read(surface_draw, surface_read) } + + fn make_current_surfaceless(&self) -> Result<()> { + self.inner.make_current_surfaceless() + } } impl GlContext for PossiblyCurrentContext { diff --git a/glutin/src/api/glx/context.rs b/glutin/src/api/glx/context.rs index 3c6df4f6c8..12189a57a2 100644 --- a/glutin/src/api/glx/context.rs +++ b/glutin/src/api/glx/context.rs @@ -241,15 +241,6 @@ pub struct NotCurrentContext { } impl NotCurrentContext { - /// Make a [`Self::PossiblyCurrentContext`] indicating that the context - /// could be current on the thread. - /// - /// Requires the GLX_ARB_create_context extension and OpenGL 3.0 or greater. - pub fn make_current_surfaceless(self) -> Result { - self.inner.make_current_surfaceless()?; - Ok(PossiblyCurrentContext { inner: self.inner, _nosendsync: PhantomData }) - } - fn new(inner: ContextInner) -> Self { Self { inner } } @@ -279,6 +270,11 @@ impl NotCurrentGlContext for NotCurrentContext { self.inner.make_current_draw_read(surface_draw, surface_read)?; Ok(PossiblyCurrentContext { inner: self.inner, _nosendsync: PhantomData }) } + + fn make_current_surfaceless(self) -> Result { + self.inner.make_current_surfaceless()?; + Ok(PossiblyCurrentContext { inner: self.inner, _nosendsync: PhantomData }) + } } impl GlContext for NotCurrentContext { @@ -319,15 +315,6 @@ pub struct PossiblyCurrentContext { _nosendsync: PhantomData, } -impl PossiblyCurrentContext { - /// Make this context current on the calling thread. - /// - /// Requires the GLX_ARB_create_context extension and OpenGL 3.0 or greater. - pub fn make_current_surfaceless(&self) -> Result<()> { - self.inner.make_current_surfaceless() - } -} - impl PossiblyCurrentGlContext for PossiblyCurrentContext { type NotCurrentContext = NotCurrentContext; type Surface = Surface; @@ -356,6 +343,10 @@ impl PossiblyCurrentGlContext for PossiblyCurrentContext { ) -> Result<()> { self.inner.make_current_draw_read(surface_draw, surface_read) } + + fn make_current_surfaceless(&self) -> Result<()> { + self.inner.make_current_surfaceless() + } } impl GlContext for PossiblyCurrentContext { diff --git a/glutin/src/api/wgl/context.rs b/glutin/src/api/wgl/context.rs index e676ba7914..67d44b2524 100644 --- a/glutin/src/api/wgl/context.rs +++ b/glutin/src/api/wgl/context.rs @@ -232,15 +232,6 @@ impl NotCurrentContext { fn new(inner: ContextInner) -> Self { Self { inner } } - - /// Make a [`Self::PossiblyCurrentContext`] indicating that the context - /// could be current on the thread. - /// - /// Requires the WGL_ARB_create_context extension and OpenGL 3.0 or greater. - pub fn make_current_surfaceless(self) -> Result { - self.inner.make_current_surfaceless()?; - Ok(PossiblyCurrentContext { inner: self.inner, _nosendsync: PhantomData }) - } } impl NotCurrentGlContext for NotCurrentContext { @@ -266,6 +257,11 @@ impl NotCurrentGlContext for NotCurrentContext { ) -> Result { Err(self.inner.make_current_draw_read(surface_draw, surface_read).into()) } + + fn make_current_surfaceless(self) -> Result { + self.inner.make_current_surfaceless()?; + Ok(PossiblyCurrentContext { inner: self.inner, _nosendsync: PhantomData }) + } } impl GlContext for NotCurrentContext { @@ -304,15 +300,6 @@ pub struct PossiblyCurrentContext { _nosendsync: PhantomData, } -impl PossiblyCurrentContext { - /// Make this context current on the calling thread. - /// - /// Requires the WGL_ARB_create_context extension and OpenGL 3.0 or greater. - pub fn make_current_surfaceless(&self) -> Result<()> { - self.inner.make_current_surfaceless() - } -} - impl PossiblyCurrentGlContext for PossiblyCurrentContext { type NotCurrentContext = NotCurrentContext; type Surface = Surface; @@ -349,6 +336,10 @@ impl PossiblyCurrentGlContext for PossiblyCurrentContext { ) -> Result<()> { Err(self.inner.make_current_draw_read(surface_draw, surface_read).into()) } + + fn make_current_surfaceless(&self) -> Result<()> { + self.inner.make_current_surfaceless() + } } impl Sealed for PossiblyCurrentContext {} diff --git a/glutin/src/context.rs b/glutin/src/context.rs index 1c1c22b04c..1abacbe33c 100644 --- a/glutin/src/context.rs +++ b/glutin/src/context.rs @@ -49,9 +49,9 @@ pub trait NotCurrentGlContext: Sealed { /// guaranteed to be current. fn treat_as_possibly_current(self) -> Self::PossiblyCurrentContext; - /// Make [`Self::Surface`] on the calling thread producing the + /// Make [`Self::Surface`] current on the calling thread producing the /// [`Self::PossiblyCurrentContext`] indicating that the context could - /// be current on the thread. + /// be current on the calling thread. /// /// # Platform specific /// @@ -67,7 +67,7 @@ pub trait NotCurrentGlContext: Sealed { /// The same as [`Self::make_current`], but provides a way to set read and /// draw surfaces. /// - /// # Api-specific: + /// # Api specific /// /// - **WGL/CGL:** not supported. fn make_current_draw_read( @@ -75,6 +75,16 @@ pub trait NotCurrentGlContext: Sealed { surface_draw: &Self::Surface, surface_read: &Self::Surface, ) -> Result; + + /// Make context current on the calling thread without a default + /// framebuffer producing the [`Self::PossiblyCurrentContext`] indicating + /// that the context could be current on the calling thread. + /// + /// # Api specific + /// + /// - **WGL/GLX:** requires OpenGL 3.0 or greater context and + /// ARB_create_context extensions. + fn make_current_surfaceless(self) -> Result; } /// A trait to group common context operations. @@ -109,10 +119,10 @@ pub trait PossiblyCurrentGlContext: Sealed { /// - **macOS: this will block if your main thread is blocked.** fn make_current(&self, surface: &Self::Surface) -> Result<()>; - /// The same as [`Self::make_current`] but provides a way to set read and + /// The same as [`Self::make_current`], but provides a way to set read and /// draw surfaces explicitly. /// - /// # Api-specific: + /// # Api specific /// /// - **CGL/WGL:** not supported. fn make_current_draw_read( @@ -120,6 +130,15 @@ pub trait PossiblyCurrentGlContext: Sealed { surface_draw: &Self::Surface, surface_read: &Self::Surface, ) -> Result<()>; + + /// Make context current on the calling thread without a default + /// framebuffer. + /// + /// # Api specific + /// + /// - **WGL/GLX:** requires OpenGL 3.0 or greater context and + /// ARB_create_context extensions. + fn make_current_surfaceless(&self) -> Result<()>; } /// A trait that provides raw context. @@ -156,7 +175,7 @@ impl ContextAttributesBuilder { /// To get sharing working it's recommended to use the same [`Config`] when /// creating contexts that are going to be shared. /// - /// # Platform-specific + /// # Platform specific /// /// - **Wayland:** both contexts must use the same Wayland connection. /// @@ -190,7 +209,7 @@ impl ContextAttributesBuilder { /// /// By default the profile is unspecified. /// - /// # Api-specific + /// # Api specific /// /// - **macOS:** not supported, the latest is picked automatically. pub fn with_profile(mut self, profile: GlProfile) -> Self { @@ -210,7 +229,7 @@ impl ContextAttributesBuilder { /// /// The `raw_window_handle` isn't required and here for WGL compatibility. /// - /// # Api-specific + /// # Api specific /// /// - **WGL:** you **must** pass a `raw_window_handle` if you plan to use /// this context with that window. @@ -338,7 +357,7 @@ pub enum ReleaseBehavior { /// Doesn't do anything. Most notably doesn't flush. Not supported by all /// drivers. /// - /// # Api-specific + /// # Api specific /// /// - **macOS:** not supported, [`Self::Flush`] is always used. None, @@ -391,6 +410,12 @@ impl NotCurrentGlContext for NotCurrentContext { gl_api_dispatch!(self; Self(context) => context.treat_as_possibly_current(); as PossiblyCurrentContext) } + fn make_current_surfaceless(self) -> Result { + Ok( + gl_api_dispatch!(self; Self(context) => context.make_current_surfaceless()?; as PossiblyCurrentContext), + ) + } + fn make_current( self, surface: &Self::Surface, @@ -522,6 +547,10 @@ impl PossiblyCurrentGlContext for PossiblyCurrentContext { ) } + fn make_current_surfaceless(&self) -> Result<()> { + gl_api_dispatch!(self; Self(context) => context.make_current_surfaceless()) + } + fn make_not_current_in_place(&self) -> Result<()> { Ok(gl_api_dispatch!(self; Self(context) => context.make_not_current_in_place()?)) } From caf2e30702106e1893a16be98e7ff8af744c2205 Mon Sep 17 00:00:00 2001 From: Kirill Chibisov Date: Tue, 12 Nov 2024 20:17:17 +0300 Subject: [PATCH 2/4] docs: update --- glutin/src/context.rs | 31 +++++++++++++++---------------- 1 file changed, 15 insertions(+), 16 deletions(-) diff --git a/glutin/src/context.rs b/glutin/src/context.rs index 1abacbe33c..95d950a43d 100644 --- a/glutin/src/context.rs +++ b/glutin/src/context.rs @@ -49,9 +49,9 @@ pub trait NotCurrentGlContext: Sealed { /// guaranteed to be current. fn treat_as_possibly_current(self) -> Self::PossiblyCurrentContext; - /// Make [`Self::Surface`] current on the calling thread producing the - /// [`Self::PossiblyCurrentContext`] indicating that the context could - /// be current on the calling thread. + /// Make context current on the calling thread producing the + /// [`Self::PossiblyCurrentContext`]. The `surface` is used as a target for + /// default framebuffer. /// /// # Platform specific /// @@ -64,8 +64,8 @@ pub trait NotCurrentGlContext: Sealed { surface: &Self::Surface, ) -> Result; - /// The same as [`Self::make_current`], but provides a way to set read and - /// draw surfaces. + /// The same as [`Self::make_current`], but provides a way to set draw and + /// read surfaces. /// /// # Api specific /// @@ -77,13 +77,12 @@ pub trait NotCurrentGlContext: Sealed { ) -> Result; /// Make context current on the calling thread without a default - /// framebuffer producing the [`Self::PossiblyCurrentContext`] indicating - /// that the context could be current on the calling thread. + /// framebuffer producing the [`Self::PossiblyCurrentContext`]. /// /// # Api specific /// /// - **WGL/GLX:** requires OpenGL 3.0 or greater context and - /// ARB_create_context extensions. + /// `ARB_create_context` extensions. fn make_current_surfaceless(self) -> Result; } @@ -99,28 +98,28 @@ pub trait PossiblyCurrentGlContext: Sealed { fn is_current(&self) -> bool; /// Make the context not current to the current thread and returns a - /// [`Self::NotCurrentContext`] to indicate that the context is a not - /// current to allow sending it to the different thread. + /// [`Self::NotCurrentContext`]. /// /// # Platform specific /// /// - **macOS: this will block if your main thread is blocked.** fn make_not_current(self) -> Result; - /// Make the context not current to the current thread. If you need to + /// Make the context not current on the current thread. If you need to /// send the context to another thread, use [`Self::make_not_current`] /// instead. fn make_not_current_in_place(&self) -> Result<()>; - /// Make [`Self::Surface`] current on the calling thread. + /// Make context current on the calling. The `surface` is used as a target + /// for default framebuffer. /// /// # Platform specific /// /// - **macOS: this will block if your main thread is blocked.** fn make_current(&self, surface: &Self::Surface) -> Result<()>; - /// The same as [`Self::make_current`], but provides a way to set read and - /// draw surfaces explicitly. + /// The same as [`Self::make_current`], but provides a way to set draw and + /// read surfaces explicitly. /// /// # Api specific /// @@ -137,7 +136,7 @@ pub trait PossiblyCurrentGlContext: Sealed { /// # Api specific /// /// - **WGL/GLX:** requires OpenGL 3.0 or greater context and - /// ARB_create_context extensions. + /// `ARB_create_context` extensions. fn make_current_surfaceless(&self) -> Result<()>; } @@ -552,7 +551,7 @@ impl PossiblyCurrentGlContext for PossiblyCurrentContext { } fn make_not_current_in_place(&self) -> Result<()> { - Ok(gl_api_dispatch!(self; Self(context) => context.make_not_current_in_place()?)) + gl_api_dispatch!(self; Self(context) => context.make_not_current_in_place()) } fn make_current(&self, surface: &Self::Surface) -> Result<()> { From 1ffe9597675be0303e9e387a866b2cf038ef26c9 Mon Sep 17 00:00:00 2001 From: Kirill Chibisov Date: Wed, 13 Nov 2024 14:36:42 +0300 Subject: [PATCH 3/4] docs: v2 --- glutin/src/context.rs | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/glutin/src/context.rs b/glutin/src/context.rs index 95d950a43d..dd6cedb766 100644 --- a/glutin/src/context.rs +++ b/glutin/src/context.rs @@ -49,9 +49,9 @@ pub trait NotCurrentGlContext: Sealed { /// guaranteed to be current. fn treat_as_possibly_current(self) -> Self::PossiblyCurrentContext; - /// Make context current on the calling thread producing the + /// Make context current on the calling thread and change its type to /// [`Self::PossiblyCurrentContext`]. The `surface` is used as a target for - /// default framebuffer. + /// the default framebuffer. /// /// # Platform specific /// @@ -77,7 +77,7 @@ pub trait NotCurrentGlContext: Sealed { ) -> Result; /// Make context current on the calling thread without a default - /// framebuffer producing the [`Self::PossiblyCurrentContext`]. + /// framebuffer and change its type to [`Self::PossiblyCurrentContext`]. /// /// # Api specific /// @@ -97,21 +97,21 @@ pub trait PossiblyCurrentGlContext: Sealed { /// Returns `true` if this context is the current one in this thread. fn is_current(&self) -> bool; - /// Make the context not current to the current thread and returns a - /// [`Self::NotCurrentContext`]. + /// Make the context not current to the current thread and change its type + /// to [`Self::NotCurrentContext`]. /// /// # Platform specific /// /// - **macOS: this will block if your main thread is blocked.** fn make_not_current(self) -> Result; - /// Make the context not current on the current thread. If you need to + /// Make the context not current on the calling thread. If you need to /// send the context to another thread, use [`Self::make_not_current`] /// instead. fn make_not_current_in_place(&self) -> Result<()>; - /// Make context current on the calling. The `surface` is used as a target - /// for default framebuffer. + /// Make context current on the calling thread. The `surface` is used as a + /// target for the default framebuffer. /// /// # Platform specific /// From 45581d9283cd8935d88ad34627efc0b8861bcbea Mon Sep 17 00:00:00 2001 From: Kirill Chibisov Date: Wed, 13 Nov 2024 15:36:49 +0300 Subject: [PATCH 4/4] Update glutin/src/context.rs Co-authored-by: Marijn Suijten --- glutin/src/context.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/glutin/src/context.rs b/glutin/src/context.rs index dd6cedb766..8e89283ec9 100644 --- a/glutin/src/context.rs +++ b/glutin/src/context.rs @@ -97,7 +97,7 @@ pub trait PossiblyCurrentGlContext: Sealed { /// Returns `true` if this context is the current one in this thread. fn is_current(&self) -> bool; - /// Make the context not current to the current thread and change its type + /// Make the context not current on the calling thread and change its type /// to [`Self::NotCurrentContext`]. /// /// # Platform specific