win64 0.0.25

Hand-crafted, idiomatic Rust wrappers for Win32
Documentation
use {
  super::{
    MessageLoopQueue,
    Msg,
    PeekMessageFlags,
  },
  crate::user::PeekResult,
  std::ops::RangeInclusive,
  windows_result::Error,
};

#[derive(Debug, Clone, PartialEq, Eq, Hash)]
pub struct MessageLoop {
  queue: MessageLoopQueue,
  filter: Option<RangeInclusive<u32>>,
  peek: Option<PeekMessageFlags>,
}

impl Default for MessageLoop {
  fn default() -> Self {
    Self::new()
  }
}

impl MessageLoop {
  pub fn new() -> MessageLoop {
    Self { queue: MessageLoopQueue::default(), filter: None, peek: None }
  }

  pub fn with_queue(mut self, queue: MessageLoopQueue) -> Self {
    self.queue = queue;
    self
  }

  pub fn with_filter(mut self, filter: Option<RangeInclusive<u32>>) -> Self {
    self.filter = filter;
    self
  }

  pub fn with_peek(mut self, flags: Option<PeekMessageFlags>) -> Self {
    self.peek = flags;
    self
  }

  pub fn run(self) {
    if self.peek.is_some() {
      self.peek(|msg| {
        if let MessageLoopResult::Peek(Some(msg)) = msg {
          msg.translate();
          msg.dispatch();
        }
      });
    } else {
      self.get(|msg| {
        if let MessageLoopResult::Get(msg) = msg {
          msg.translate();
          msg.dispatch();
        }
      });
    }
  }

  pub fn run_with(self, f: impl Fn(MessageLoopResult)) {
    if self.peek.is_some() {
      self.peek(f);
    } else {
      self.get(f);
    }
  }

  fn peek(&self, f: impl Fn(MessageLoopResult)) {
    for msg in Msg::peek(MessageLoopQueue::Thread, None, PeekMessageFlags::Remove) {
      f(match msg {
        PeekResult::Msg(msg) => MessageLoopResult::Peek(Some(msg)),
        PeekResult::None => MessageLoopResult::Peek(None),
        PeekResult::Err(error) => MessageLoopResult::Err(error),
      });
    }
  }

  fn get(&self, f: impl Fn(MessageLoopResult)) {
    for msg in Msg::get(MessageLoopQueue::Thread, None) {
      f(match msg {
        Ok(msg) => MessageLoopResult::Get(msg),
        Err(error) => MessageLoopResult::Err(error),
      });
    }
  }
}

#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
pub enum MessageLoopResult {
  Peek(Option<Msg>),
  Get(Msg),
  Err(Error),
}