mirror of
https://github.com/italicsjenga/winit-sonoma-fix.git
synced 2024-12-23 22:01:31 +11:00
Merge pull request #8 from tomaka/breaking-api-changes
Add WindowBuilder and iterators for events
This commit is contained in:
commit
af756b9add
|
@ -5,8 +5,6 @@ extern crate gl;
|
|||
use std::io::stdio::stdin;
|
||||
|
||||
fn main() {
|
||||
use std::default::Default;
|
||||
|
||||
// enumerating monitors
|
||||
let monitor = {
|
||||
for (num, monitor) in init::get_available_monitors().enumerate() {
|
||||
|
@ -23,8 +21,11 @@ fn main() {
|
|||
monitor
|
||||
};
|
||||
|
||||
let window = init::Window::new(None, "Hello world!", &Default::default(),
|
||||
Some(monitor)).unwrap();
|
||||
let window = init::WindowBuilder::new()
|
||||
.with_title("Hello world!".to_string())
|
||||
.with_monitor(monitor)
|
||||
.build()
|
||||
.unwrap();
|
||||
|
||||
unsafe { window.make_current() };
|
||||
|
||||
|
@ -40,7 +41,7 @@ fn main() {
|
|||
gl::ClearColor(0.0, 1.0, 0.0, 1.0);
|
||||
|
||||
while !window.is_closed() {
|
||||
println!("{}", window.wait_events());
|
||||
println!("{}", window.wait_events().collect::<Vec<init::Event>>());
|
||||
|
||||
gl::Clear(gl::COLOR_BUFFER_BIT);
|
||||
|
||||
|
|
|
@ -3,9 +3,7 @@ extern crate libc;
|
|||
extern crate gl;
|
||||
|
||||
fn main() {
|
||||
use std::default::Default;
|
||||
|
||||
let window = init::Window::new(None, "Hello world!", &Default::default(), None).unwrap();
|
||||
let window = init::Window::new().unwrap();
|
||||
|
||||
unsafe { window.make_current() };
|
||||
|
||||
|
@ -21,7 +19,7 @@ fn main() {
|
|||
gl::ClearColor(0.0, 1.0, 0.0, 1.0);
|
||||
|
||||
while !window.is_closed() {
|
||||
println!("{}", window.wait_events());
|
||||
println!("{}", window.wait_events().collect::<Vec<init::Event>>());
|
||||
|
||||
gl::Clear(gl::COLOR_BUFFER_BIT);
|
||||
|
||||
|
|
74
src/hints.rs
74
src/hints.rs
|
@ -1,74 +0,0 @@
|
|||
use std::default::Default;
|
||||
|
||||
#[deriving(Clone,Show)]
|
||||
#[deprecated = "Will be removed soon (it's not supported anyway)"]
|
||||
pub struct Hints {
|
||||
pub resizable: bool,
|
||||
pub visible: bool,
|
||||
pub decorated: bool,
|
||||
pub red_bits: u8,
|
||||
pub green_bits: u8,
|
||||
pub blue_bits: u8,
|
||||
pub alpha_bits: u8,
|
||||
pub depth_bits: u8,
|
||||
pub stencil_bits: u8,
|
||||
pub accum_red_bits: u8,
|
||||
pub accum_green_bits: u8,
|
||||
pub accum_blue_bits: u8,
|
||||
pub accum_alpha_bits: u8,
|
||||
pub aux_buffers: u8,
|
||||
pub samples: u8,
|
||||
pub refresh_rate: u8,
|
||||
pub stereo: bool,
|
||||
pub srgb_capable: bool,
|
||||
pub client_api: ClientAPI,
|
||||
pub context_version: (u8, u8),
|
||||
//pub robustness: ,
|
||||
pub opengl_forward_compat: bool,
|
||||
pub opengl_debug_context: bool,
|
||||
pub opengl_profile: Profile,
|
||||
}
|
||||
|
||||
#[deriving(Clone, Show)]
|
||||
pub enum ClientAPI {
|
||||
OpenGL,
|
||||
OpenGLES,
|
||||
}
|
||||
|
||||
#[deriving(Clone, Show)]
|
||||
pub enum Profile {
|
||||
AnyProfile,
|
||||
CompatProfile,
|
||||
CoreProfile,
|
||||
}
|
||||
|
||||
impl Default for Hints {
|
||||
fn default() -> Hints {
|
||||
Hints {
|
||||
resizable: true,
|
||||
visible: true,
|
||||
decorated: true,
|
||||
red_bits: 8,
|
||||
green_bits: 8,
|
||||
blue_bits: 8,
|
||||
alpha_bits: 8,
|
||||
depth_bits: 24,
|
||||
stencil_bits: 8,
|
||||
accum_red_bits: 0,
|
||||
accum_green_bits: 0,
|
||||
accum_blue_bits: 0,
|
||||
accum_alpha_bits: 0,
|
||||
aux_buffers: 0,
|
||||
samples: 0,
|
||||
refresh_rate: 0,
|
||||
stereo: false,
|
||||
srgb_capable: false,
|
||||
client_api: OpenGL,
|
||||
context_version: (1, 0),
|
||||
//robustness: ,
|
||||
opengl_forward_compat: false,
|
||||
opengl_debug_context: false,
|
||||
opengl_profile: AnyProfile,
|
||||
}
|
||||
}
|
||||
}
|
147
src/lib.rs
147
src/lib.rs
|
@ -5,7 +5,6 @@
|
|||
extern crate libc;
|
||||
|
||||
pub use events::*;
|
||||
pub use hints::{Hints, ClientAPI, Profile};
|
||||
|
||||
#[cfg(windows)]
|
||||
use winimpl = win32;
|
||||
|
@ -21,19 +20,63 @@ mod x11;
|
|||
//mod egl;
|
||||
|
||||
mod events;
|
||||
mod hints;
|
||||
|
||||
/// Identifier for a monitor.
|
||||
pub struct MonitorID(winimpl::MonitorID);
|
||||
|
||||
/// Object that allows you to build windows.
|
||||
pub struct WindowBuilder {
|
||||
dimensions: (uint, uint),
|
||||
title: String,
|
||||
monitor: Option<winimpl::MonitorID>,
|
||||
}
|
||||
|
||||
impl WindowBuilder {
|
||||
/// Initializes a new `WindowBuilder` with default values.
|
||||
pub fn new() -> WindowBuilder {
|
||||
WindowBuilder {
|
||||
dimensions: (1024, 768),
|
||||
title: String::new(),
|
||||
monitor: None,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn with_dimensions(mut self, width: uint, height: uint) -> WindowBuilder {
|
||||
self.dimensions = (width, height);
|
||||
self
|
||||
}
|
||||
|
||||
pub fn with_title(mut self, title: String) -> WindowBuilder {
|
||||
self.title = title;
|
||||
self
|
||||
}
|
||||
|
||||
pub fn with_monitor(mut self, monitor: MonitorID) -> WindowBuilder {
|
||||
let MonitorID(monitor) = monitor;
|
||||
self.monitor = Some(monitor);
|
||||
self
|
||||
}
|
||||
|
||||
/// Builds the window.
|
||||
///
|
||||
/// Error should be very rare and only occur in case of permission denied, incompatible system,
|
||||
/// out of memory, etc.
|
||||
pub fn build(self) -> Result<Window, String> {
|
||||
let win = try!(winimpl::Window::new(Some(self.dimensions),
|
||||
self.title.as_slice(), self.monitor));
|
||||
|
||||
Ok(Window{
|
||||
window: win,
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
/// Represents an OpenGL context and the Window or environment around it.
|
||||
///
|
||||
/// # Example
|
||||
///
|
||||
/// ```
|
||||
/// use std::default::Default;
|
||||
///
|
||||
/// let window = Window::new(None, "Hello world!", &Default::default(), None).unwrap();
|
||||
/// let window = Window::new().unwrap();
|
||||
///
|
||||
/// unsafe { window.make_current() };
|
||||
///
|
||||
|
@ -57,43 +100,15 @@ pub struct Window {
|
|||
|
||||
impl Window {
|
||||
/// Creates a new OpenGL context, and a Window for platforms where this is appropriate.
|
||||
///
|
||||
/// This function is equivalent to `WindowBuilder::new().build()`.
|
||||
///
|
||||
/// # Parameters
|
||||
///
|
||||
/// The `dimensions` parameter tell the library what the dimensions of the client area
|
||||
/// of the window must be. If set to `None`, the library will choose or let the O/S choose.
|
||||
///
|
||||
/// The `title` parameter is the title that the window must have.
|
||||
///
|
||||
/// The `hints` parameter must be a `Hint` object which contains hints about how the context
|
||||
/// must be created. This library will *try* to follow the hints, but will still success
|
||||
/// even if it could not conform to all of them.
|
||||
///
|
||||
/// The `monitor` parameter is the identifier of the monitor that this window should fill.
|
||||
/// If `None`, a windowed window will be created. If `Some(_)`, the window will be fullscreen
|
||||
/// and will fill the given monitor. Note `MonitorID` does not necessarly represent a
|
||||
/// *physical* monitor.
|
||||
///
|
||||
/// # Return value
|
||||
///
|
||||
/// Returns the `Window` object.
|
||||
///
|
||||
/// Error should be very rare and only occur in case of permission denied, incompatible system,
|
||||
/// out of memory, etc.
|
||||
#[inline]
|
||||
pub fn new(dimensions: Option<(uint, uint)>, title: &str,
|
||||
hints: &Hints, monitor: Option<MonitorID>)
|
||||
-> Result<Window, String>
|
||||
{
|
||||
// extracting the monitor ID
|
||||
let monitor = monitor.map(|id| { let MonitorID(id) = id; id });
|
||||
|
||||
// creating the window
|
||||
let win = try!(winimpl::Window::new(dimensions, title, hints, monitor));
|
||||
|
||||
Ok(Window{
|
||||
window: win,
|
||||
})
|
||||
pub fn new() -> Result<Window, String> {
|
||||
let builder = WindowBuilder::new();
|
||||
builder.build()
|
||||
}
|
||||
|
||||
/// Returns true if the window has previously been closed by the user.
|
||||
|
@ -176,32 +191,22 @@ impl Window {
|
|||
self.window.set_inner_size(x, y)
|
||||
}
|
||||
|
||||
/// Returns all the events that are currently in window's events queue.
|
||||
/// Returns an iterator to all the events that are currently in the window's events queue.
|
||||
///
|
||||
/// Contrary to `wait_events`, this function never blocks.
|
||||
#[experimental = "Will probably be changed to return an iterator instead of a Vec"]
|
||||
#[inline]
|
||||
pub fn poll_events(&self) -> Vec<Event> {
|
||||
self.window.poll_events()
|
||||
pub fn poll_events(&self) -> PollEventsIterator {
|
||||
PollEventsIterator { data: self.window.poll_events() }
|
||||
}
|
||||
|
||||
/// Returns all the events that are currently in window's events queue.
|
||||
/// If there are no events in queue, this function will block until there is one.
|
||||
///
|
||||
/// This is equivalent to:
|
||||
///
|
||||
/// ```
|
||||
/// loop {
|
||||
/// let events = poll_events();
|
||||
/// if events.len() >= 1 { return events }
|
||||
/// }
|
||||
/// ```
|
||||
///
|
||||
/// ...but without the spinlock.
|
||||
/// Waits for an event, then returns an iterator to all the events that are currently
|
||||
/// in the window's events queue.
|
||||
///
|
||||
/// If there are no events in queue when you call the function,
|
||||
/// this function will block until there is one.
|
||||
#[inline]
|
||||
#[experimental = "Will probably be changed to return an iterator instead of a Vec"]
|
||||
pub fn wait_events(&self) -> Vec<Event> {
|
||||
self.window.wait_events()
|
||||
pub fn wait_events(&self) -> WaitEventsIterator {
|
||||
WaitEventsIterator { data: self.window.wait_events() }
|
||||
}
|
||||
|
||||
/// Sets the context as the current context.
|
||||
|
@ -229,6 +234,32 @@ impl Window {
|
|||
}
|
||||
}
|
||||
|
||||
/// An iterator for the `poll_events` function.
|
||||
// Implementation note: we retreive the list once, then serve each element by one by one.
|
||||
// This may change in the future.
|
||||
pub struct PollEventsIterator<'a> {
|
||||
data: Vec<Event>,
|
||||
}
|
||||
|
||||
impl<'a> Iterator<Event> for PollEventsIterator<'a> {
|
||||
fn next(&mut self) -> Option<Event> {
|
||||
self.data.remove(0)
|
||||
}
|
||||
}
|
||||
|
||||
/// An iterator for the `wait_events` function.
|
||||
// Implementation note: we retreive the list once, then serve each element by one by one.
|
||||
// This may change in the future.
|
||||
pub struct WaitEventsIterator<'a> {
|
||||
data: Vec<Event>,
|
||||
}
|
||||
|
||||
impl<'a> Iterator<Event> for WaitEventsIterator<'a> {
|
||||
fn next(&mut self) -> Option<Event> {
|
||||
self.data.remove(0)
|
||||
}
|
||||
}
|
||||
|
||||
/// An iterator for the list of available monitors.
|
||||
// Implementation note: we retreive the list once, then serve each element by one by one.
|
||||
// This may change in the future.
|
||||
|
|
|
@ -6,7 +6,7 @@ use std::sync::atomics::AtomicBool;
|
|||
use std::ptr;
|
||||
use super::{event, ffi};
|
||||
use super::{MonitorID, Window};
|
||||
use {Event, Hints};
|
||||
use Event;
|
||||
|
||||
/// Stores the current window and its events dispatcher.
|
||||
///
|
||||
|
@ -15,7 +15,7 @@ use {Event, Hints};
|
|||
local_data_key!(WINDOW: (ffi::HWND, Sender<Event>))
|
||||
|
||||
pub fn new_window(dimensions: Option<(uint, uint)>, title: &str,
|
||||
_hints: &Hints, monitor: Option<MonitorID>)
|
||||
monitor: Option<MonitorID>)
|
||||
-> Result<Window, String>
|
||||
{
|
||||
use std::mem;
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
use std::sync::atomics::AtomicBool;
|
||||
use std::ptr;
|
||||
use {Event, Hints};
|
||||
use Event;
|
||||
|
||||
pub use self::monitor::{MonitorID, get_available_monitors, get_primary_monitor};
|
||||
|
||||
|
@ -36,10 +36,10 @@ pub struct Window {
|
|||
impl Window {
|
||||
/// See the docs if the crate root file.
|
||||
pub fn new(dimensions: Option<(uint, uint)>, title: &str,
|
||||
hints: &Hints, monitor: Option<MonitorID>)
|
||||
monitor: Option<MonitorID>)
|
||||
-> Result<Window, String>
|
||||
{
|
||||
init::new_window(dimensions, title, hints, monitor)
|
||||
init::new_window(dimensions, title, monitor)
|
||||
}
|
||||
|
||||
/// See the docs if the crate root file.
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
use {Event, Hints};
|
||||
use Event;
|
||||
use libc;
|
||||
use std::{mem, ptr};
|
||||
use std::sync::atomics::AtomicBool;
|
||||
|
@ -33,7 +33,7 @@ impl MonitorID {
|
|||
}
|
||||
|
||||
impl Window {
|
||||
pub fn new(dimensions: Option<(uint, uint)>, title: &str, hints: &Hints, _: Option<MonitorID>)
|
||||
pub fn new(dimensions: Option<(uint, uint)>, title: &str, _: Option<MonitorID>)
|
||||
-> Result<Window, String>
|
||||
{
|
||||
// calling XOpenDisplay
|
||||
|
|
Loading…
Reference in a new issue