diff --git a/Cargo.lock b/Cargo.lock index bb6455f..312a0c3 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -4579,10 +4579,12 @@ dependencies = [ name = "omni-led" version = "0.11.0" dependencies = [ + "clap", "log", "log4rs", "mlua", "omni-led-lib", + "windows 0.62.2", ] [[package]] diff --git a/omni-led/Cargo.toml b/omni-led/Cargo.toml index 058bebb..4e428dd 100644 --- a/omni-led/Cargo.toml +++ b/omni-led/Cargo.toml @@ -7,10 +7,14 @@ edition = "2024" default-run = "omni-led" [dependencies] +clap = { version = "4.5", features = ["derive"] } log = { version = "0.4", features = ["std"] } log4rs = "1.4" mlua = "0.11" omni-led-lib = { path = "../omni-led-lib" } +[target.'cfg(target_os = "windows")'.dependencies] +windows = { version = "0.62", features = ["Win32_System_Console"] } + [features] dev = ["omni-led-lib/dev"] diff --git a/omni-led/src/console.rs b/omni-led/src/console.rs new file mode 100644 index 0000000..dbe6cbf --- /dev/null +++ b/omni-led/src/console.rs @@ -0,0 +1,14 @@ +use windows::Win32::System::Console::{AttachConsole, GetConsoleWindow}; + +pub fn attach_console_if_missing() { + if !has_console() { + const ATTACH_PARENT_PROCESS: u32 = u32::MAX; + unsafe { + _ = AttachConsole(ATTACH_PARENT_PROCESS); + } + } +} + +fn has_console() -> bool { + unsafe { !GetConsoleWindow().is_invalid() } +} diff --git a/omni-led/src/main.rs b/omni-led/src/main.rs index 953f68e..268e329 100644 --- a/omni-led/src/main.rs +++ b/omni-led/src/main.rs @@ -1,5 +1,6 @@ #![cfg_attr(not(feature = "dev"), windows_subsystem = "windows")] +use clap::Parser; use log::debug; use mlua::Lua; use omni_led_lib::{ @@ -24,11 +25,30 @@ use std::sync; use std::sync::atomic::{AtomicBool, Ordering}; use std::time::Instant; +#[cfg(target_os = "windows")] +mod console; mod logging; static RUNNING: AtomicBool = AtomicBool::new(true); fn main() { + let _options = match Options::try_parse() { + Ok(options) => { + #[cfg(target_os = "windows")] + if options.attach_console { + console::attach_console_if_missing(); + } + + options + } + Err(err) => { + #[cfg(target_os = "windows")] + console::attach_console_if_missing(); + + err.exit(); + } + }; + set_panic_hook(); let (ready_tx, ready_rx) = sync::mpsc::channel(); @@ -100,3 +120,12 @@ fn set_panic_hook() { hook(info); })); } + +#[derive(Parser)] +#[command(name = "OmniLED")] +#[command(version, about)] +struct Options { + /// Attach console to the program. Applies only on Windows. + #[clap(short, long, default_value = "false")] + attach_console: bool, +}