Mac OS においてデバッグするときには、NSLog を呼ばないととにかくやりづらい、というときがあります(InputMethodKit を使った開発をするときなどが特にそうです)。 そんなときには、以下の様にすると良いでしょう。
use cocoa::base::{id, nil};
use cocoa::foundation::NSString;
#[link(name = "Foundation", kind = "framework")]
extern {
pub fn NSLog(fmt: id, ...);
}
fn main() {
unsafe {
NSLog(NSString::alloc(nil).init_str("Hello, %@"), NSString::alloc(nil).init_str("world"));
}
}
Dependency は以下のように Cargo.toml に記述します。
[package]
name = "rust-nslog-sample"
version = "0.1.0"
edition = "2021"
[dependencies]
cocoa = "0.24.0"
さて、とはいえ毎回 NSString だなんだと書くのはめんどくさい、というのはあるかも。 せめて最初の引数はマクロ化したいですよね。
↓マクロ化するならこんな感じかな?
use cocoa::base::{id, nil};
use cocoa::foundation::NSString;
#[link(name = "Foundation", kind = "framework")]
extern {
pub fn NSLog(fmt: id, ...);
}
macro_rules! NSLog {
( $fmt:expr ) => {
unsafe {
NSLog(NSString::alloc(nil).init_str($fmt))
}
};
( $fmt:expr, $( $x:expr ),* ) => {
unsafe {
NSLog(NSString::alloc(nil).init_str($fmt), $($x, )*)
}
};
}
fn main() {
unsafe {
NSLog!("Hello, %@ %d", NSString::alloc(nil).init_str("world"), 5963);
}
}