diff --git a/Cargo.toml b/Cargo.toml index 8eb2d66..2deec97 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -14,7 +14,7 @@ all-features = true [features] default = ["xlib"] -glx = ["x11/glx", "xlib"] +glx = ["x11/glx", "xlib", "gl_generator"] xlib = ["x11/xlib"] xrender = ["x11/xrender"] xinerama = ["x11/xinerama", "xlib"] @@ -26,3 +26,6 @@ x11 = { version = "2.18" } thiserror = "1.0.20" log = "0.4.8" bitflags = "1.2.1" + +[build-dependencies] +gl_generator = { version = "0.14.0", optional = true } diff --git a/build.rs b/build.rs new file mode 100644 index 0000000..ca96342 --- /dev/null +++ b/build.rs @@ -0,0 +1,14 @@ +use std::env; +use std::fs::File; +use std::path::Path; + +use gl_generator::{Api, Fallbacks, GlobalGenerator, Profile, Registry}; + +fn main() { + let dest = env::var("OUT_DIR").unwrap(); + let mut file = File::create(&Path::new(&dest).join("bindings.rs")).unwrap(); + + Registry::new(Api::Gl, (4, 5), Profile::Core, Fallbacks::All, []) + .write_bindings(GlobalGenerator, &mut file) + .unwrap(); +} diff --git a/src/glx/context.rs b/src/glx/context.rs new file mode 100644 index 0000000..f3023bf --- /dev/null +++ b/src/glx/context.rs @@ -0,0 +1,20 @@ +use x11::glx; + +use crate::xlib::Display; + +pub struct GlxContext<'a> { + pub(super) display: &'a Display, + pub(super) ctx: glx::GLXContext, +} + +impl<'a> GlxContext<'a> { + pub fn as_raw(&self) -> glx::GLXContext { + self.ctx + } +} + +impl<'a> Drop for GlxContext<'a> { + fn drop(&mut self) { + unsafe { glx::glXDestroyContext(self.display.as_raw(), self.ctx) }; + } +} diff --git a/src/glx/mod.rs b/src/glx/mod.rs index 1de3256..af75a1f 100644 --- a/src/glx/mod.rs +++ b/src/glx/mod.rs @@ -1,10 +1,16 @@ +mod context; + use x11::glx; use crate::errors::Result; use crate::xlib::Display; +pub use self::context::GlxContext; + pub trait GlxExtension { fn query_glx_extension(&self) -> Result; + + fn create_context(&self, share_list: Option<&GlxContext>, direct: bool) -> Result; } impl GlxExtension for Display { @@ -12,4 +18,13 @@ impl GlxExtension for Display { let result = unsafe { glx::glXQueryExtension(self.inner, 0 as *mut _, 0 as *mut _) }; Ok(result == 1) } + + fn create_context(&self, share_list: Option<&GlxContext>, direct: bool) -> Result { + let share_list = share_list + .map(|ctx| ctx.as_raw()) + .unwrap_or_else(|| 0 as *mut _); + let ctx = + unsafe { glx::glXCreateContext(self.as_raw(), 0 as *mut _, share_list, direct.into()) }; + Ok(GlxContext { display: self, ctx }) + } } diff --git a/src/lib.rs b/src/lib.rs index a9fc641..42e5c4e 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -9,6 +9,10 @@ extern crate log; pub extern crate x11; +#[cfg(feature = "glx")] +mod gl { + include!(concat!(env!("OUT_DIR"), "/bindings.rs")); +} #[cfg(feature = "glx")] pub mod glx;