egl: move surface creation into `NativeSurface`
This commit is contained in:
parent
4647141770
commit
0267703e91
|
@ -5,15 +5,17 @@
|
||||||
//!
|
//!
|
||||||
|
|
||||||
use crate::backend::drm::{Device, RawDevice, Surface};
|
use crate::backend::drm::{Device, RawDevice, Surface};
|
||||||
use crate::backend::egl::ffi;
|
|
||||||
use crate::backend::egl::native::{Backend, NativeDisplay, NativeSurface};
|
use crate::backend::egl::native::{Backend, NativeDisplay, NativeSurface};
|
||||||
|
use crate::backend::egl::{display::EGLDisplayHandle, ffi};
|
||||||
use crate::backend::egl::{wrap_egl_call, EGLError, Error as EglBackendError};
|
use crate::backend::egl::{wrap_egl_call, EGLError, Error as EglBackendError};
|
||||||
|
|
||||||
use super::{Error, GbmDevice, GbmSurface};
|
use super::{Error, GbmDevice, GbmSurface};
|
||||||
|
|
||||||
use drm::control::{connector, crtc, Device as ControlDevice, Mode};
|
use drm::control::{connector, crtc, Device as ControlDevice, Mode};
|
||||||
use gbm::AsRaw;
|
use gbm::AsRaw;
|
||||||
|
use nix::libc::{c_int, c_void};
|
||||||
use std::marker::PhantomData;
|
use std::marker::PhantomData;
|
||||||
|
use std::ptr;
|
||||||
|
|
||||||
/// Egl Gbm backend type
|
/// Egl Gbm backend type
|
||||||
///
|
///
|
||||||
|
@ -80,10 +82,18 @@ unsafe impl<D: RawDevice + ControlDevice + 'static> NativeDisplay<Gbm<D>> for Gb
|
||||||
}
|
}
|
||||||
|
|
||||||
unsafe impl<D: RawDevice + 'static> NativeSurface for GbmSurface<D> {
|
unsafe impl<D: RawDevice + 'static> NativeSurface for GbmSurface<D> {
|
||||||
type Error = Error<<<D as RawDevice>::Surface as Surface>::Error>;
|
unsafe fn create(
|
||||||
|
&self,
|
||||||
fn ptr(&self) -> ffi::NativeWindowType {
|
display: &EGLDisplayHandle,
|
||||||
self.0.surface.borrow().as_raw() as *const _
|
config_id: ffi::egl::types::EGLConfig,
|
||||||
|
surface_attributes: &[c_int],
|
||||||
|
) -> *const c_void {
|
||||||
|
ffi::egl::CreateWindowSurface(
|
||||||
|
display.handle,
|
||||||
|
config_id,
|
||||||
|
self.0.surface.borrow().as_raw() as *const _,
|
||||||
|
surface_attributes.as_ptr(),
|
||||||
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn needs_recreation(&self) -> bool {
|
fn needs_recreation(&self) -> bool {
|
||||||
|
|
|
@ -30,8 +30,9 @@ use std::ops::Deref;
|
||||||
|
|
||||||
/// Wrapper around [`ffi::EGLDisplay`](ffi::egl::types::EGLDisplay) to ensure display is only destroyed
|
/// Wrapper around [`ffi::EGLDisplay`](ffi::egl::types::EGLDisplay) to ensure display is only destroyed
|
||||||
/// once all resources bound to it have been dropped.
|
/// once all resources bound to it have been dropped.
|
||||||
pub(crate) struct EGLDisplayHandle {
|
pub struct EGLDisplayHandle {
|
||||||
handle: ffi::egl::types::EGLDisplay,
|
/// ffi EGLDisplay ptr
|
||||||
|
pub handle: ffi::egl::types::EGLDisplay,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Deref for EGLDisplayHandle {
|
impl Deref for EGLDisplayHandle {
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
//! Type safe native types for safe context/surface creation
|
//! Type safe native types for safe context/surface creation
|
||||||
|
|
||||||
use super::{ffi, wrap_egl_call, EGLError, Error};
|
use super::{display::EGLDisplayHandle, ffi, wrap_egl_call, EGLError, Error, SurfaceCreationError};
|
||||||
|
use nix::libc::{c_int, c_void};
|
||||||
|
|
||||||
#[cfg(feature = "backend_winit")]
|
#[cfg(feature = "backend_winit")]
|
||||||
use wayland_egl as wegl;
|
use wayland_egl as wegl;
|
||||||
|
@ -200,8 +201,13 @@ pub unsafe trait NativeSurface {
|
||||||
/// Error of the underlying surface
|
/// Error of the underlying surface
|
||||||
type Error: std::error::Error;
|
type Error: std::error::Error;
|
||||||
|
|
||||||
/// Return a raw pointer egl will accept for surface creation.
|
/// Create an EGLSurface from the internal native type
|
||||||
fn ptr(&self) -> ffi::NativeWindowType;
|
unsafe fn create(
|
||||||
|
&self,
|
||||||
|
display: &EGLDisplayHandle,
|
||||||
|
config_id: ffi::egl::types::EGLConfig,
|
||||||
|
surface_attributes: &[c_int],
|
||||||
|
) -> Result<*const c_void, SurfaceCreationError<Self::Error>>;
|
||||||
|
|
||||||
/// Will be called to check if any internal resources will need
|
/// Will be called to check if any internal resources will need
|
||||||
/// to be recreated. Old resources must be used until `recreate`
|
/// to be recreated. Old resources must be used until `recreate`
|
||||||
|
@ -247,8 +253,21 @@ unsafe impl NativeSurface for XlibWindow {
|
||||||
// type Error = !; (https://github.com/rust-lang/rust/issues/35121)
|
// type Error = !; (https://github.com/rust-lang/rust/issues/35121)
|
||||||
type Error = Never;
|
type Error = Never;
|
||||||
|
|
||||||
fn ptr(&self) -> ffi::NativeWindowType {
|
unsafe fn create(
|
||||||
self.0 as *const _
|
&self,
|
||||||
|
display: &EGLDisplayHandle,
|
||||||
|
config_id: ffi::egl::types::EGLConfig,
|
||||||
|
surface_attributes: &[c_int],
|
||||||
|
) -> Result<*const c_void, SurfaceCreationError<Never>> {
|
||||||
|
wrap_egl_call(|| {
|
||||||
|
ffi::egl::CreateWindowSurface(
|
||||||
|
display.handle,
|
||||||
|
config_id,
|
||||||
|
self.0 as *const _,
|
||||||
|
surface_attributes.as_ptr(),
|
||||||
|
)
|
||||||
|
})
|
||||||
|
.map_err(SurfaceCreationError::EGLSurfaceCreationFailed)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -257,7 +276,20 @@ unsafe impl NativeSurface for wegl::WlEglSurface {
|
||||||
// type Error = !;
|
// type Error = !;
|
||||||
type Error = Never;
|
type Error = Never;
|
||||||
|
|
||||||
fn ptr(&self) -> ffi::NativeWindowType {
|
unsafe fn create(
|
||||||
self.ptr() as *const _
|
&self,
|
||||||
|
display: &EGLDisplayHandle,
|
||||||
|
config_id: ffi::egl::types::EGLConfig,
|
||||||
|
surface_attributes: &[c_int],
|
||||||
|
) -> Result<*const c_void, SurfaceCreationError<Never>> {
|
||||||
|
wrap_egl_call(|| {
|
||||||
|
ffi::egl::CreateWindowSurface(
|
||||||
|
display.handle,
|
||||||
|
config_id,
|
||||||
|
self.ptr() as *const _,
|
||||||
|
surface_attributes.as_ptr(),
|
||||||
|
)
|
||||||
|
})
|
||||||
|
.map_err(SurfaceCreationError::EGLSurfaceCreationFailed)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -69,9 +69,7 @@ impl<N: native::NativeSurface> EGLSurface<N> {
|
||||||
out
|
out
|
||||||
};
|
};
|
||||||
|
|
||||||
let surface = wrap_egl_call(|| unsafe {
|
let surface = unsafe { native.create(&*display, config, &surface_attributes)? };
|
||||||
ffi::egl::CreateWindowSurface(**display, config, native.ptr(), surface_attributes.as_ptr())
|
|
||||||
})?;
|
|
||||||
|
|
||||||
if surface == ffi::egl::NO_SURFACE {
|
if surface == ffi::egl::NO_SURFACE {
|
||||||
return Err(EGLError::BadSurface);
|
return Err(EGLError::BadSurface);
|
||||||
|
@ -112,16 +110,12 @@ impl<N: native::NativeSurface> EGLSurface<N> {
|
||||||
if !surface.is_null() {
|
if !surface.is_null() {
|
||||||
let _ = unsafe { ffi::egl::DestroySurface(**self.display, surface as *const _) };
|
let _ = unsafe { ffi::egl::DestroySurface(**self.display, surface as *const _) };
|
||||||
}
|
}
|
||||||
|
//TODO remove recreate
|
||||||
|
self.native.recreate();
|
||||||
self.surface.set(unsafe {
|
self.surface.set(unsafe {
|
||||||
wrap_egl_call(|| {
|
self.native
|
||||||
ffi::egl::CreateWindowSurface(
|
.create(&*self.display, self.config_id, &self.surface_attributes)
|
||||||
**self.display,
|
.map_err(SwapBuffersError::EGLCreateWindowSurface)?
|
||||||
self.config_id,
|
|
||||||
self.native.ptr(),
|
|
||||||
self.surface_attributes.as_ptr(),
|
|
||||||
)
|
|
||||||
})
|
|
||||||
.map_err(SwapBuffersError::EGLCreateWindowSurface)?
|
|
||||||
});
|
});
|
||||||
|
|
||||||
result.map_err(|err| {
|
result.map_err(|err| {
|
||||||
|
|
Loading…
Reference in New Issue