diff options
-rw-r--r-- | .travis.yml | 2 | ||||
-rw-r--r-- | Cargo.toml | 2 | ||||
-rw-r--r-- | build.rs | 2 | ||||
-rw-r--r-- | examples/multiwindow.rs | 6 | ||||
-rw-r--r-- | src/android/mod.rs | 5 | ||||
-rw-r--r-- | src/cocoa/mod.rs | 28 | ||||
-rw-r--r-- | src/win32/init.rs | 8 | ||||
-rw-r--r-- | src/win32/mod.rs | 8 | ||||
-rw-r--r-- | src/win32/monitor.rs | 11 | ||||
-rw-r--r-- | src/window.rs | 6 | ||||
-rw-r--r-- | src/x11/window/mod.rs | 37 |
11 files changed, 93 insertions, 22 deletions
diff --git a/.travis.yml b/.travis.yml index 5a26936..b4c12ba 100644 --- a/.travis.yml +++ b/.travis.yml @@ -4,8 +4,6 @@ rust: - nightly - 1.0.0-beta -sudo: false - addons: apt: packages: @@ -1,6 +1,6 @@ [package] name = "glutin" -version = "0.0.23" +version = "0.0.25" authors = ["tomaka <pierre.krieger1708@gmail.com>"] description = "Cross-plaform OpenGL context provider." keywords = ["windowing", "opengl"] @@ -52,6 +52,8 @@ fn main() { khronos_api::GLX_XML, vec![ "GLX_ARB_create_context".to_string(), + "GLX_ARB_framebuffer_sRGB".to_string(), + "GLX_EXT_framebuffer_sRGB".to_string(), "GLX_EXT_swap_control".to_string(), "GLX_SGI_swap_control".to_string() ], diff --git a/examples/multiwindow.rs b/examples/multiwindow.rs index ce97266..a9a5bac 100644 --- a/examples/multiwindow.rs +++ b/examples/multiwindow.rs @@ -20,15 +20,15 @@ fn main() { let window2 = glutin::Window::new().unwrap(); let window3 = glutin::Window::new().unwrap(); - let t1 = thread::scoped(move || { + let t1 = thread::spawn(move || { run(window1, (0.0, 1.0, 0.0, 1.0)); }); - let t2 = thread::scoped(move || { + let t2 = thread::spawn(move || { run(window2, (0.0, 0.0, 1.0, 1.0)); }); - let t3 = thread::scoped(move || { + let t3 = thread::spawn(move || { run(window3, (1.0, 0.0, 0.0, 1.0)); }); diff --git a/src/android/mod.rs b/src/android/mod.rs index 5c7096c..5e71aed 100644 --- a/src/android/mod.rs +++ b/src/android/mod.rs @@ -15,6 +15,7 @@ use Api; use BuilderAttribs; use CursorState; use GlRequest; +use PixelFormat; use native_monitor::NativeMonitorId; pub struct Window { @@ -353,6 +354,10 @@ impl Window { ::Api::OpenGlEs } + pub fn get_pixel_format(&self) -> PixelFormat { + unimplemented!(); + } + pub fn set_window_resize_callback(&mut self, _: Option<fn(u32, u32)>) { } diff --git a/src/cocoa/mod.rs b/src/cocoa/mod.rs index 6b97964..506967b 100644 --- a/src/cocoa/mod.rs +++ b/src/cocoa/mod.rs @@ -8,6 +8,7 @@ use libc; use Api; use BuilderAttribs; use GlRequest; +use PixelFormat; use native_monitor::NativeMonitorId; use objc::runtime::{Class, Object, Sel, BOOL, YES, NO}; @@ -32,7 +33,7 @@ use std::sync::Mutex; use std::ascii::AsciiExt; use std::ops::Deref; -use events::Event::{Awakened, MouseInput, MouseMoved, ReceivedCharacter, KeyboardInput, MouseWheel}; +use events::Event::{Awakened, MouseInput, MouseMoved, ReceivedCharacter, KeyboardInput, MouseWheel, Closed}; use events::ElementState::{Pressed, Released}; use events::MouseButton; use events; @@ -56,6 +57,9 @@ struct DelegateState { view: IdRef, window: IdRef, resize_handler: Option<fn(u32, u32)>, + + /// Events that have been retreived with XLib but not dispatched with iterators yet + pending_events: Mutex<VecDeque<Event>>, } struct WindowDelegate { @@ -73,6 +77,8 @@ impl WindowDelegate { let state: *mut libc::c_void = *this.get_ivar("glutinState"); let state = state as *mut DelegateState; (*state).is_closed = true; + + (*state).pending_events.lock().unwrap().push_back(Closed); } YES } @@ -147,9 +153,6 @@ pub struct Window { window: IdRef, context: IdRef, delegate: WindowDelegate, - - /// Events that have been retreived with XLib but not dispatched with iterators yet - pending_events: Mutex<VecDeque<Event>>, } #[cfg(feature = "window")] @@ -183,7 +186,7 @@ impl<'a> Iterator for PollEventsIterator<'a> { type Item = Event; fn next(&mut self) -> Option<Event> { - if let Some(ev) = self.window.pending_events.lock().unwrap().pop_front() { + if let Some(ev) = self.window.delegate.state.pending_events.lock().unwrap().pop_front() { return Some(ev); } @@ -231,7 +234,7 @@ impl<'a> Iterator for PollEventsIterator<'a> { let vkey = event::vkeycode_to_element(NSEvent::keyCode(event)); events.push_back(KeyboardInput(Pressed, NSEvent::keyCode(event) as u8, vkey)); let event = events.pop_front(); - self.window.pending_events.lock().unwrap().extend(events.into_iter()); + self.window.delegate.state.pending_events.lock().unwrap().extend(events.into_iter()); event }, NSKeyUp => { @@ -261,13 +264,15 @@ impl<'a> Iterator for PollEventsIterator<'a> { events.push_back(alt_modifier.unwrap()); } let event = events.pop_front(); - self.window.pending_events.lock().unwrap().extend(events.into_iter()); + self.window.delegate.state.pending_events.lock().unwrap().extend(events.into_iter()); event }, NSScrollWheel => { Some(MouseWheel(event.scrollingDeltaY() as i32)) }, _ => { None }, }; + + event } } @@ -282,7 +287,7 @@ impl<'a> Iterator for WaitEventsIterator<'a> { fn next(&mut self) -> Option<Event> { loop { - if let Some(ev) = self.window.pending_events.lock().unwrap().pop_front() { + if let Some(ev) = self.window.delegate.state.pending_events.lock().unwrap().pop_front() { return Some(ev); } @@ -347,6 +352,7 @@ impl Window { view: view.clone(), window: window.clone(), resize_handler: None, + pending_events: Mutex::new(VecDeque::new()), }; let window = Window { @@ -354,8 +360,6 @@ impl Window { window: window, context: context, delegate: WindowDelegate::new(ds), - - pending_events: Mutex::new(VecDeque::new()), }; Ok(window) @@ -616,6 +620,10 @@ impl Window { ::Api::OpenGl } + pub fn get_pixel_format(&self) -> PixelFormat { + unimplemented!(); + } + pub fn set_window_resize_callback(&mut self, callback: Option<fn(u32, u32)>) { self.delegate.state.resize_handler = callback; } diff --git a/src/win32/init.rs b/src/win32/init.rs index 743508e..5cdd6b8 100644 --- a/src/win32/init.rs +++ b/src/win32/init.rs @@ -203,16 +203,17 @@ unsafe fn init(title: Vec<u16>, builder: BuilderAttribs<'static>, }; // calling SetPixelFormat - { + let pixel_format = { let formats = if extra_functions.GetPixelFormatAttribivARB.is_loaded() { enumerate_arb_pixel_formats(&extra_functions, &real_window) } else { enumerate_native_pixel_formats(&real_window) }; - let (id, _) = try!(builder.choose_pixel_format(formats.into_iter().map(|(a, b)| (b, a)))); + let (id, f) = try!(builder.choose_pixel_format(formats.into_iter().map(|(a, b)| (b, a)))); try!(set_pixel_format(&real_window, id)); - } + f + }; // creating the OpenGL context let context = try!(create_context(Some((&extra_functions, &builder)), &real_window, @@ -263,6 +264,7 @@ unsafe fn init(title: Vec<u16>, builder: BuilderAttribs<'static>, events_receiver: events_receiver, is_closed: AtomicBool::new(false), cursor_state: cursor_state, + pixel_format: pixel_format, }) } diff --git a/src/win32/mod.rs b/src/win32/mod.rs index 1f5f3c0..4a9dcbf 100644 --- a/src/win32/mod.rs +++ b/src/win32/mod.rs @@ -13,6 +13,7 @@ use libc; use {CreationError, Event, MouseCursor}; use CursorState; +use PixelFormat; use BuilderAttribs; pub use self::headless::HeadlessContext; @@ -53,6 +54,9 @@ pub struct Window { /// The current cursor state. cursor_state: Arc<Mutex<CursorState>>, + + /// The pixel format that has been used to create this window. + pixel_format: PixelFormat, } unsafe impl Send for Window {} @@ -258,6 +262,10 @@ impl Window { ::Api::OpenGl } + pub fn get_pixel_format(&self) -> PixelFormat { + self.pixel_format.clone() + } + pub fn set_window_resize_callback(&mut self, _: Option<fn(u32, u32)>) { } diff --git a/src/win32/monitor.rs b/src/win32/monitor.rs index 886d0bf..4b592cb 100644 --- a/src/win32/monitor.rs +++ b/src/win32/monitor.rs @@ -21,6 +21,9 @@ pub struct MonitorID { /// http://msdn.microsoft.com/en-us/library/dd183569(v=vs.85).aspx flags: winapi::DWORD, + /// True if this is the primary monitor. + primary: bool, + /// The position of the monitor in pixels on the desktop. /// /// A window that is positionned at these coordinates will overlap the monitor. @@ -114,13 +117,15 @@ pub fn get_available_monitors() -> VecDeque<MonitorID> { (position, dimensions) }; - for monitor in DeviceEnumerator::monitors(adapter.DeviceName.as_ptr()) { + for (num, monitor) in DeviceEnumerator::monitors(adapter.DeviceName.as_ptr()).enumerate() { // adding to the resulting list result.push_back(MonitorID { adapter_name: adapter.DeviceName, monitor_name: wchar_as_string(&monitor.DeviceName), readable_name: wchar_as_string(&monitor.DeviceString), flags: monitor.StateFlags, + primary: (adapter.StateFlags & winapi::DISPLAY_DEVICE_PRIMARY_DEVICE) != 0 && + num == 0, position: position, dimensions: dimensions, }); @@ -135,8 +140,8 @@ pub fn get_primary_monitor() -> MonitorID { // TODO: it is possible to query the win32 API for the primary monitor, this should be done // instead for monitor in get_available_monitors().into_iter() { - if (monitor.flags & winapi::DISPLAY_DEVICE_PRIMARY_DEVICE) != 0 { - return monitor + if monitor.primary { + return monitor; } } diff --git a/src/window.rs b/src/window.rs index bf040b0..dee4ce5 100644 --- a/src/window.rs +++ b/src/window.rs @@ -8,6 +8,7 @@ use CursorState; use Event; use GlRequest; use MouseCursor; +use PixelFormat; use native_monitor::NativeMonitorId; use gl_common; @@ -388,6 +389,11 @@ impl Window { self.window.get_api() } + /// Returns the pixel format of this window. + pub fn get_pixel_format(&self) -> PixelFormat { + self.window.get_pixel_format() + } + /// Create a window proxy for this window, that can be freely /// passed to different threads. #[inline] diff --git a/src/x11/window/mod.rs b/src/x11/window/mod.rs index 270746f..84b9625 100644 --- a/src/x11/window/mod.rs +++ b/src/x11/window/mod.rs @@ -12,6 +12,7 @@ use std::sync::{Arc, Mutex, Once, ONCE_INIT}; use Api; use CursorState; use GlRequest; +use PixelFormat; pub use self::monitor::{MonitorID, get_available_monitors, get_primary_monitor}; @@ -278,6 +279,7 @@ pub struct Window { is_closed: AtomicBool, wm_delete_window: ffi::Atom, current_size: Cell<(libc::c_int, libc::c_int)>, + pixel_format: PixelFormat, /// Events that have been retreived with XLib but not dispatched with iterators yet pending_events: Mutex<VecDeque<Event>>, cursor_state: Mutex<CursorState>, @@ -325,6 +327,11 @@ impl Window { visual_attributes.push(val as libc::c_int); } + if let Some(val) = builder.srgb { + visual_attributes.push(ffi::glx_extra::FRAMEBUFFER_SRGB_CAPABLE_ARB as libc::c_int); + visual_attributes.push(if val {1} else {0}); + } + visual_attributes.push(0); let mut num_fb: libc::c_int = mem::uninitialized(); @@ -375,6 +382,31 @@ impl Window { vi_copy }; + // querying the chosen pixel format + let pixel_format = { + let get_attrib = |attrib: libc::c_int| -> i32 { + let mut value = 0; + unsafe { ffi::glx::GetFBConfigAttrib(display, fb_config, attrib, &mut value); } + value + }; + + PixelFormat { + hardware_accelerated: true, + red_bits: get_attrib(ffi::GLX_RED_SIZE) as u8, + green_bits: get_attrib(ffi::GLX_GREEN_SIZE) as u8, + blue_bits: get_attrib(ffi::GLX_BLUE_SIZE) as u8, + alpha_bits: get_attrib(ffi::GLX_ALPHA_SIZE) as u8, + depth_bits: get_attrib(ffi::GLX_DEPTH_SIZE) as u8, + stencil_bits: get_attrib(ffi::GLX_STENCIL_SIZE) as u8, + stereoscopy: get_attrib(ffi::GLX_STEREO) != 0, + double_buffer: get_attrib(ffi::GLX_DOUBLEBUFFER) != 0, + multisampling: if get_attrib(ffi::glx::SAMPLE_BUFFERS as libc::c_int) != 0 { + Some(get_attrib(ffi::glx::SAMPLES as libc::c_int) as u16) + }else { None }, + srgb: get_attrib(ffi::glx_extra::FRAMEBUFFER_SRGB_CAPABLE_ARB as libc::c_int) != 0, + } + }; + // getting the root window let root = unsafe { ffi::XDefaultRootWindow(display) }; @@ -597,6 +629,7 @@ impl Window { is_closed: AtomicBool::new(false), wm_delete_window: wm_delete_window, current_size: Cell::new((0, 0)), + pixel_format: pixel_format, pending_events: Mutex::new(VecDeque::new()), cursor_state: Mutex::new(CursorState::Normal), }; @@ -730,6 +763,10 @@ impl Window { ::Api::OpenGl } + pub fn get_pixel_format(&self) -> PixelFormat { + self.pixel_format.clone() + } + pub fn set_window_resize_callback(&mut self, _: Option<fn(u32, u32)>) { } |