mirror of
https://github.com/italicsjenga/rust_minifb.git
synced 2025-01-11 11:31:32 +11:00
WIP on Mac version
This commit is contained in:
parent
026be10b8b
commit
1455bd375e
94
src/macos.rs
94
src/macos.rs
|
@ -25,6 +25,7 @@ pub struct Window {
|
||||||
view: IdRef,
|
view: IdRef,
|
||||||
window: IdRef,
|
window: IdRef,
|
||||||
delegate: WindowDelegate,
|
delegate: WindowDelegate,
|
||||||
|
view_delegate: ViewDelegate,
|
||||||
}
|
}
|
||||||
|
|
||||||
struct DelegateState {
|
struct DelegateState {
|
||||||
|
@ -38,7 +39,14 @@ struct WindowDelegate {
|
||||||
_this: IdRef,
|
_this: IdRef,
|
||||||
}
|
}
|
||||||
|
|
||||||
//sthou
|
struct ViewDelegateState {
|
||||||
|
view: IdRef,
|
||||||
|
}
|
||||||
|
|
||||||
|
struct ViewDelegate {
|
||||||
|
state: Box<ViewDelegateState>,
|
||||||
|
_this: IdRef,
|
||||||
|
}
|
||||||
|
|
||||||
impl WindowDelegate {
|
impl WindowDelegate {
|
||||||
/// Get the delegate class, initiailizing it neccessary
|
/// Get the delegate class, initiailizing it neccessary
|
||||||
|
@ -46,9 +54,10 @@ impl WindowDelegate {
|
||||||
use std::sync::{Once, ONCE_INIT};
|
use std::sync::{Once, ONCE_INIT};
|
||||||
|
|
||||||
extern fn window_should_close(this: &Object, _: Sel, _: id) -> BOOL {
|
extern fn window_should_close(this: &Object, _: Sel, _: id) -> BOOL {
|
||||||
|
println!("Should close");
|
||||||
unsafe {
|
unsafe {
|
||||||
let state: *mut libc::c_void = *this.get_ivar("glutinState");
|
//let state: *mut libc::c_void = *this.get_ivar("minifb_window_state");
|
||||||
let state = state as *mut DelegateState;
|
//let state = state as *mut DelegateState;
|
||||||
//(*state).pending_events.lock().unwrap().push_back(Closed);
|
//(*state).pending_events.lock().unwrap().push_back(Closed);
|
||||||
}
|
}
|
||||||
YES
|
YES
|
||||||
|
@ -56,7 +65,7 @@ impl WindowDelegate {
|
||||||
|
|
||||||
extern fn window_did_resize(this: &Object, _: Sel, _: id) {
|
extern fn window_did_resize(this: &Object, _: Sel, _: id) {
|
||||||
unsafe {
|
unsafe {
|
||||||
let state: *mut libc::c_void = *this.get_ivar("glutinState");
|
let state: *mut libc::c_void = *this.get_ivar("minifb_window_state");
|
||||||
let state = &mut *(state as *mut DelegateState);
|
let state = &mut *(state as *mut DelegateState);
|
||||||
|
|
||||||
println!("did_resize");
|
println!("did_resize");
|
||||||
|
@ -78,7 +87,7 @@ impl WindowDelegate {
|
||||||
// lost focus
|
// lost focus
|
||||||
|
|
||||||
println!("became key window");
|
println!("became key window");
|
||||||
let state: *mut libc::c_void = *this.get_ivar("glutinState");
|
let state: *mut libc::c_void = *this.get_ivar("minifb_window_state");
|
||||||
let state = state as *mut DelegateState;
|
let state = state as *mut DelegateState;
|
||||||
//(*state).pending_events.lock().unwrap().push_back(Focused(true));
|
//(*state).pending_events.lock().unwrap().push_back(Focused(true));
|
||||||
}
|
}
|
||||||
|
@ -86,7 +95,7 @@ impl WindowDelegate {
|
||||||
|
|
||||||
extern fn window_did_resign_key(this: &Object, _: Sel, _: id) {
|
extern fn window_did_resign_key(this: &Object, _: Sel, _: id) {
|
||||||
unsafe {
|
unsafe {
|
||||||
let state: *mut libc::c_void = *this.get_ivar("glutinState");
|
let state: *mut libc::c_void = *this.get_ivar("minifb_window_state");
|
||||||
let state = state as *mut DelegateState;
|
let state = state as *mut DelegateState;
|
||||||
//(*state).pending_events.lock().unwrap().push_back(Focused(false));
|
//(*state).pending_events.lock().unwrap().push_back(Focused(false));
|
||||||
}
|
}
|
||||||
|
@ -98,7 +107,7 @@ impl WindowDelegate {
|
||||||
INIT.call_once(|| unsafe {
|
INIT.call_once(|| unsafe {
|
||||||
println!("Create new NSWindowDelegate");
|
println!("Create new NSWindowDelegate");
|
||||||
let superclass = Class::get("NSObject").unwrap();
|
let superclass = Class::get("NSObject").unwrap();
|
||||||
let mut decl = ClassDecl::new(superclass, "GlutinWindowDelegate").unwrap();
|
let mut decl = ClassDecl::new(superclass, "minifb_window_delegate").unwrap();
|
||||||
|
|
||||||
// Add callback methods
|
// Add callback methods
|
||||||
decl.add_method(sel!(windowShouldClose:),
|
decl.add_method(sel!(windowShouldClose:),
|
||||||
|
@ -112,7 +121,7 @@ impl WindowDelegate {
|
||||||
window_did_resign_key as extern fn(&Object, Sel, id));
|
window_did_resign_key as extern fn(&Object, Sel, id));
|
||||||
|
|
||||||
// Store internal state as user data
|
// Store internal state as user data
|
||||||
decl.add_ivar::<*mut libc::c_void>("glutinState");
|
decl.add_ivar::<*mut libc::c_void>("minifb_window_state");
|
||||||
|
|
||||||
delegate_class = decl.register();
|
delegate_class = decl.register();
|
||||||
});
|
});
|
||||||
|
@ -129,9 +138,11 @@ impl WindowDelegate {
|
||||||
unsafe {
|
unsafe {
|
||||||
let delegate = IdRef::new(msg_send![WindowDelegate::class(), new]);
|
let delegate = IdRef::new(msg_send![WindowDelegate::class(), new]);
|
||||||
|
|
||||||
(&mut **delegate).set_ivar("glutinState", state_ptr as *mut libc::c_void);
|
(&mut **delegate).set_ivar("minifb_window_state", state_ptr as *mut libc::c_void);
|
||||||
let _: () = msg_send![*state.window, setDelegate:*delegate];
|
let _: () = msg_send![*state.window, setDelegate:*delegate];
|
||||||
|
|
||||||
|
println!("Setup delegate");
|
||||||
|
|
||||||
WindowDelegate { state: state, _this: delegate }
|
WindowDelegate { state: state, _this: delegate }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -146,6 +157,60 @@ impl Drop for WindowDelegate {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl ViewDelegate {
|
||||||
|
fn class() -> *const Class {
|
||||||
|
use std::sync::{Once, ONCE_INIT};
|
||||||
|
|
||||||
|
extern fn draw_rect(this: &Object, _: Sel, _: id) {
|
||||||
|
println!("draw_rect");
|
||||||
|
}
|
||||||
|
|
||||||
|
static mut delegate_class: *const Class = 0 as *const Class;
|
||||||
|
static INIT: Once = ONCE_INIT;
|
||||||
|
|
||||||
|
INIT.call_once(|| unsafe {
|
||||||
|
println!("Create new ViewDelegate");
|
||||||
|
let superclass = Class::get("NSObject").unwrap();
|
||||||
|
let mut decl = ClassDecl::new(superclass, "minifb_view_delegate").unwrap();
|
||||||
|
|
||||||
|
// Add callback methods
|
||||||
|
decl.add_method(sel!(drawRect:),
|
||||||
|
draw_rect as extern fn(&Object, Sel, id));
|
||||||
|
// Store internal state as user data
|
||||||
|
decl.add_ivar::<*mut libc::c_void>("minifb_view_state");
|
||||||
|
|
||||||
|
delegate_class = decl.register();
|
||||||
|
});
|
||||||
|
|
||||||
|
unsafe {
|
||||||
|
delegate_class
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn new(state: ViewDelegateState) -> ViewDelegate {
|
||||||
|
let mut state = Box::new(state);
|
||||||
|
let state_ptr: *mut ViewDelegateState = &mut *state;
|
||||||
|
unsafe {
|
||||||
|
let delegate = IdRef::new(msg_send![ViewDelegate::class(), new]);
|
||||||
|
|
||||||
|
(&mut **delegate).set_ivar("minifb_view_state", state_ptr as *mut libc::c_void);
|
||||||
|
let _: () = msg_send![*state.view, setDelegate:*delegate];
|
||||||
|
|
||||||
|
ViewDelegate { state: state, _this: delegate }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Drop for ViewDelegate {
|
||||||
|
fn drop(&mut self) {
|
||||||
|
unsafe {
|
||||||
|
// Nil the views's delegate so it doesn't still reference us
|
||||||
|
let _: () = msg_send![*self.state.view, setDelegate:nil];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
impl Window {
|
impl Window {
|
||||||
pub fn new(name: &str, width: usize, height: usize, _: Scale, _: Vsync) -> Result<Window, &str> {
|
pub fn new(name: &str, width: usize, height: usize, _: Scale, _: Vsync) -> Result<Window, &str> {
|
||||||
|
@ -180,12 +245,17 @@ impl Window {
|
||||||
resize_handler: None,
|
resize_handler: None,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
let vs = ViewDelegateState {
|
||||||
|
view: view.clone(),
|
||||||
|
};
|
||||||
|
|
||||||
println!("Created window and view");
|
println!("Created window and view");
|
||||||
|
|
||||||
return Ok(Window {
|
return Ok(Window {
|
||||||
window: window,
|
window: window,
|
||||||
view: view,
|
view: view,
|
||||||
delegate: WindowDelegate::new(ds),
|
delegate: WindowDelegate::new(ds),
|
||||||
|
view_delegate: ViewDelegate::new(vs),
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -223,11 +293,15 @@ impl Window {
|
||||||
|
|
||||||
pub fn update(&self, _: &[u32]) {
|
pub fn update(&self, _: &[u32]) {
|
||||||
unsafe {
|
unsafe {
|
||||||
NSApp().nextEventMatchingMask_untilDate_inMode_dequeue_(
|
let event = NSApp().nextEventMatchingMask_untilDate_inMode_dequeue_(
|
||||||
NSAnyEventMask.bits(),
|
NSAnyEventMask.bits(),
|
||||||
NSDate::distantPast(nil),
|
NSDate::distantPast(nil),
|
||||||
NSDefaultRunLoopMode,
|
NSDefaultRunLoopMode,
|
||||||
YES);
|
YES);
|
||||||
|
|
||||||
|
if event != nil {
|
||||||
|
NSApp().sendEvent_(event);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue