diff --git a/examples/fullscreen.rs b/examples/fullscreen.rs
index b6141a0e..80e60899 100644
--- a/examples/fullscreen.rs
+++ b/examples/fullscreen.rs
@@ -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);
 
diff --git a/examples/window.rs b/examples/window.rs
index daa856b7..c366ee0a 100644
--- a/examples/window.rs
+++ b/examples/window.rs
@@ -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);
 
diff --git a/src/hints.rs b/src/hints.rs
deleted file mode 100644
index aaa9a807..00000000
--- a/src/hints.rs
+++ /dev/null
@@ -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,
-        }
-    }
-}
diff --git a/src/lib.rs b/src/lib.rs
index 83a75a44..155900d0 100644
--- a/src/lib.rs
+++ b/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.
diff --git a/src/win32/init.rs b/src/win32/init.rs
index db08a428..ce558dcd 100644
--- a/src/win32/init.rs
+++ b/src/win32/init.rs
@@ -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;
diff --git a/src/win32/mod.rs b/src/win32/mod.rs
index 75582455..0d44a75c 100644
--- a/src/win32/mod.rs
+++ b/src/win32/mod.rs
@@ -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.
diff --git a/src/x11/mod.rs b/src/x11/mod.rs
index 76339f56..bc89aed5 100644
--- a/src/x11/mod.rs
+++ b/src/x11/mod.rs
@@ -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