Merge pull request #6 from glowcoil/master
unify api and file structure across platforms; make example platform-independent
This commit is contained in:
commit
c4aabbdac1
|
@ -1,5 +1,3 @@
|
|||
use std::ptr::null_mut;
|
||||
|
||||
fn main() {
|
||||
let window_open_options = baseview::WindowOpenOptions {
|
||||
title: "baseview",
|
||||
|
@ -8,18 +6,5 @@ fn main() {
|
|||
parent: baseview::Parent::None,
|
||||
};
|
||||
|
||||
#[cfg(target_os = "macos")] {
|
||||
baseview::Window::open(window_open_options);
|
||||
}
|
||||
#[cfg(target_os = "windows")] {
|
||||
baseview::create_window(window_open_options);
|
||||
loop {
|
||||
if !baseview::handle_msg(null_mut()) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
#[cfg(target_os = "linux")] {
|
||||
baseview::run(window_open_options);
|
||||
}
|
||||
baseview::Window::open(window_open_options);
|
||||
}
|
||||
|
|
11
src/lib.rs
11
src/lib.rs
|
@ -4,12 +4,16 @@ use std::ffi::c_void;
|
|||
mod win;
|
||||
#[cfg(target_os = "windows")]
|
||||
pub use win::*;
|
||||
|
||||
#[cfg(target_os = "linux")]
|
||||
mod x11;
|
||||
#[cfg(target_os = "linux")]
|
||||
pub use x11::*;
|
||||
|
||||
#[cfg(target_os = "macos")]
|
||||
mod macos;
|
||||
#[cfg(target_os = "macos")]
|
||||
pub use macos::Window;
|
||||
pub use macos::*;
|
||||
|
||||
pub enum Parent {
|
||||
None,
|
||||
|
@ -25,8 +29,3 @@ pub struct WindowOpenOptions<'a> {
|
|||
|
||||
pub parent: Parent,
|
||||
}
|
||||
|
||||
#[cfg(target_os = "linux")]
|
||||
pub fn run(options: WindowOpenOptions) {
|
||||
x11::run(options);
|
||||
}
|
||||
|
|
2
src/macos/mod.rs
Normal file
2
src/macos/mod.rs
Normal file
|
@ -0,0 +1,2 @@
|
|||
mod window;
|
||||
pub use window::*;
|
|
@ -11,7 +11,7 @@ use crate::WindowOpenOptions;
|
|||
pub struct Window;
|
||||
|
||||
impl Window {
|
||||
pub fn open(options: WindowOpenOptions) {
|
||||
pub fn open(options: WindowOpenOptions) -> Self {
|
||||
unsafe {
|
||||
let _pool = NSAutoreleasePool::new(nil);
|
||||
|
||||
|
@ -41,6 +41,8 @@ impl Window {
|
|||
let current_app = NSRunningApplication::currentApplication(nil);
|
||||
current_app.activateWithOptions_(NSApplicationActivateIgnoringOtherApps);
|
||||
app.run();
|
||||
|
||||
Window
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,3 +1,2 @@
|
|||
mod window;
|
||||
|
||||
pub use window::*;
|
||||
|
|
|
@ -1,5 +1,7 @@
|
|||
extern crate winapi;
|
||||
|
||||
use std::ptr::null_mut;
|
||||
|
||||
use self::winapi::_core::mem::MaybeUninit;
|
||||
use self::winapi::shared::guiddef::GUID;
|
||||
use self::winapi::shared::minwindef::{LPARAM, LPVOID, LRESULT, UINT, WPARAM};
|
||||
|
@ -14,7 +16,75 @@ use self::winapi::um::winuser::{
|
|||
|
||||
use crate::WindowOpenOptions;
|
||||
|
||||
pub fn handle_msg(_window: HWND) -> bool {
|
||||
pub struct Window;
|
||||
|
||||
impl Window {
|
||||
pub fn open(options: WindowOpenOptions) -> Self {
|
||||
unsafe {
|
||||
// We generate a unique name for the new window class to prevent name collisions
|
||||
let mut guid: GUID = MaybeUninit::uninit().assume_init();
|
||||
CoCreateGuid(&mut guid);
|
||||
let class_name = format!(
|
||||
"Baseview-{}-{}-{}-{}{}{}{}{}{}{}{}\0",
|
||||
guid.Data1,
|
||||
guid.Data2,
|
||||
guid.Data3,
|
||||
guid.Data4[0],
|
||||
guid.Data4[1],
|
||||
guid.Data4[2],
|
||||
guid.Data4[3],
|
||||
guid.Data4[4],
|
||||
guid.Data4[5],
|
||||
guid.Data4[6],
|
||||
guid.Data4[7]
|
||||
);
|
||||
|
||||
let hinstance = GetModuleHandleA(0 as *const i8);
|
||||
let wnd_class = WNDCLASSA {
|
||||
// todo: for OpenGL, will use it later
|
||||
style: CS_OWNDC | CS_HREDRAW | CS_VREDRAW,
|
||||
lpfnWndProc: Some(wnd_proc),
|
||||
hInstance: hinstance,
|
||||
lpszClassName: class_name.as_ptr() as *const i8,
|
||||
cbClsExtra: 0,
|
||||
cbWndExtra: 0,
|
||||
hIcon: 0 as HICON,
|
||||
hCursor: 0 as HICON,
|
||||
hbrBackground: 0 as HBRUSH,
|
||||
lpszMenuName: 0 as *const i8,
|
||||
};
|
||||
RegisterClassA(&wnd_class);
|
||||
|
||||
let _hwnd = CreateWindowExA(
|
||||
0,
|
||||
class_name.as_ptr() as *const i8,
|
||||
// todo: change title based on options struct
|
||||
"Baseview\0".as_ptr() as *const i8,
|
||||
// todo: fine for now, will have to change with a parent
|
||||
WS_OVERLAPPEDWINDOW | WS_VISIBLE,
|
||||
CW_USEDEFAULT,
|
||||
CW_USEDEFAULT,
|
||||
// todo: check if usize fits into i32
|
||||
options.width as i32,
|
||||
options.height as i32,
|
||||
0 as HWND,
|
||||
0 as HMENU,
|
||||
hinstance,
|
||||
0 as LPVOID,
|
||||
);
|
||||
|
||||
loop {
|
||||
if !handle_msg(null_mut()) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Window
|
||||
}
|
||||
}
|
||||
|
||||
fn handle_msg(_window: HWND) -> bool {
|
||||
unsafe {
|
||||
let mut msg: MSG = MaybeUninit::uninit().assume_init();
|
||||
loop {
|
||||
|
@ -30,7 +100,7 @@ pub fn handle_msg(_window: HWND) -> bool {
|
|||
}
|
||||
}
|
||||
|
||||
pub unsafe extern "system" fn wnd_proc(
|
||||
unsafe extern "system" fn wnd_proc(
|
||||
hwnd: HWND,
|
||||
msg: UINT,
|
||||
w_param: WPARAM,
|
||||
|
@ -46,59 +116,3 @@ pub unsafe extern "system" fn wnd_proc(
|
|||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
pub fn create_window(w: WindowOpenOptions) {
|
||||
unsafe {
|
||||
// We generate a unique name for the new window class to prevent name collisions
|
||||
let mut guid: GUID = MaybeUninit::uninit().assume_init();
|
||||
CoCreateGuid(&mut guid);
|
||||
let class_name = format!(
|
||||
"Baseview-{}-{}-{}-{}{}{}{}{}{}{}{}\0",
|
||||
guid.Data1,
|
||||
guid.Data2,
|
||||
guid.Data3,
|
||||
guid.Data4[0],
|
||||
guid.Data4[1],
|
||||
guid.Data4[2],
|
||||
guid.Data4[3],
|
||||
guid.Data4[4],
|
||||
guid.Data4[5],
|
||||
guid.Data4[6],
|
||||
guid.Data4[7]
|
||||
);
|
||||
|
||||
let hinstance = GetModuleHandleA(0 as *const i8);
|
||||
let wnd_class = WNDCLASSA {
|
||||
// todo: for OpenGL, will use it later
|
||||
style: CS_OWNDC | CS_HREDRAW | CS_VREDRAW,
|
||||
lpfnWndProc: Some(wnd_proc),
|
||||
hInstance: hinstance,
|
||||
lpszClassName: class_name.as_ptr() as *const i8,
|
||||
cbClsExtra: 0,
|
||||
cbWndExtra: 0,
|
||||
hIcon: 0 as HICON,
|
||||
hCursor: 0 as HICON,
|
||||
hbrBackground: 0 as HBRUSH,
|
||||
lpszMenuName: 0 as *const i8,
|
||||
};
|
||||
RegisterClassA(&wnd_class);
|
||||
|
||||
let _hwnd = CreateWindowExA(
|
||||
0,
|
||||
class_name.as_ptr() as *const i8,
|
||||
// todo: change title based on options struct
|
||||
"Baseview\0".as_ptr() as *const i8,
|
||||
// todo: fine for now, will have to change with a parent
|
||||
WS_OVERLAPPEDWINDOW | WS_VISIBLE,
|
||||
CW_USEDEFAULT,
|
||||
CW_USEDEFAULT,
|
||||
// todo: check if usize fits into i32
|
||||
w.width as i32,
|
||||
w.height as i32,
|
||||
0 as HWND,
|
||||
0 as HMENU,
|
||||
hinstance,
|
||||
0 as LPVOID,
|
||||
);
|
||||
}
|
||||
}
|
||||
|
|
2
src/x11/mod.rs
Normal file
2
src/x11/mod.rs
Normal file
|
@ -0,0 +1,2 @@
|
|||
mod window;
|
||||
pub use window::*;
|
|
@ -8,12 +8,12 @@
|
|||
use crate::Parent;
|
||||
use crate::WindowOpenOptions;
|
||||
|
||||
struct X11Window {
|
||||
pub struct Window {
|
||||
xcb_connection: xcb::Connection,
|
||||
}
|
||||
|
||||
impl X11Window {
|
||||
pub fn run(options: WindowOpenOptions) -> Self {
|
||||
impl Window {
|
||||
pub fn open(options: WindowOpenOptions) -> Self {
|
||||
// Convert the parent to a X11 window ID if we're given one
|
||||
let parent = match options.parent {
|
||||
Parent::None => None,
|
||||
|
@ -107,10 +107,6 @@ impl X11Window {
|
|||
}
|
||||
}
|
||||
|
||||
pub fn run(options: WindowOpenOptions) {
|
||||
X11Window::run(options);
|
||||
}
|
||||
|
||||
// Figure out the DPI scaling by opening a new temporary connection and asking XCB
|
||||
// TODO: currently returning (96, 96) on my system, even though I have 4k screens. Problem with my setup perhaps?
|
||||
#[allow(dead_code)]
|
Loading…
Reference in a new issue