aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
author魏曹先生 <1992414357@qq.com>2026-06-20 07:20:46 +0800
committer魏曹先生 <1992414357@qq.com>2026-06-20 07:32:54 +0800
commit9b896d697eb582dedd2533f6d2054f062c8381a0 (patch)
treeb7e8db33af8e6837f3d389d4302b821d401ec0d8 /src
parent69354929928d1d071698262c259cdffbf9aec468 (diff)
feat: add custom help message and fix clap help conflict
Disable clap's built-in help flag and reroute `-h`/`--help` to print an embedded help text from `help.txt`. Use `try_parse` to avoid clap's default exit on parse failure, allowing custom error output.
Diffstat (limited to 'src')
-rw-r--r--src/args.rs6
-rw-r--r--src/main.rs28
-rw-r--r--src/output_protocol/ipc.rs2
3 files changed, 25 insertions, 11 deletions
diff --git a/src/args.rs b/src/args.rs
index 52dddfc..c27ff78 100644
--- a/src/args.rs
+++ b/src/args.rs
@@ -14,9 +14,15 @@ macro_rules! debug_log {
};
}
+/// The full help text embedded at compile time.
+pub static HELP_TEXT: &str = include_str!("../help.txt");
+
#[derive(clap::Parser)]
#[command(name = "dmvop", disable_help_flag = true, disable_version_flag = true)]
pub struct DMVOPArguments {
+ // Show help
+ #[arg(long = "help", short = 'h')]
+ pub help: bool,
// Verbose output (show debug messages)
#[arg(long = "verbose", short = 'V')]
pub verbose: bool,
diff --git a/src/main.rs b/src/main.rs
index 875ac39..15f23f7 100644
--- a/src/main.rs
+++ b/src/main.rs
@@ -8,8 +8,6 @@ use std::path::PathBuf;
use std::sync::Arc;
use vtx_engine::EngineBuilder;
-/// Output channel enum — wraps each OutputProtocol implementation so we can
-/// store a heterogeneous collection and dispatch `send` without trait objects.
enum OutputChannel {
Stdout(Arc<output_protocol::StandardOutputProtocol>),
Stderr(Arc<output_protocol::StandardErrorProtocol>),
@@ -58,7 +56,19 @@ async fn main() {
.with_target(false)
.init();
- let args = DMVOPArguments::parse();
+ let args = match DMVOPArguments::try_parse() {
+ Ok(a) => a,
+ Err(_) => {
+ eprintln!("error: invalid arguments. Use --help for usage.");
+ std::process::exit(1);
+ }
+ };
+
+ // Handle --help immediately
+ if args.help {
+ print!("{}", HELP_TEXT);
+ return;
+ }
// Set global verbose flag
VERBOSE.store(args.verbose, std::sync::atomic::Ordering::Relaxed);
@@ -86,7 +96,7 @@ async fn main() {
}
// ---------------------------------------------------------------
- // 1. Build the vtx-engine (needed for both listing and capture)
+ // Build the vtx-engine (needed for both listing and capture)
// ---------------------------------------------------------------
debug_log!("[dmvop] Initializing voice engine...");
@@ -138,7 +148,7 @@ async fn main() {
}
// ---------------------------------------------------------------
- // 2. List devices and exit?
+ // List devices and exit?
// ---------------------------------------------------------------
let devices = engine.list_input_devices();
@@ -158,12 +168,12 @@ async fn main() {
}
// ---------------------------------------------------------------
- // 3. Resolve the format pattern
+ // Resolve the format pattern
// ---------------------------------------------------------------
let pattern = resolve_format_pattern(args.format_pattern.as_deref(), args.format_file.as_ref());
// ---------------------------------------------------------------
- // 4. Create and initialize output channels
+ // Create and initialize output channels
// ---------------------------------------------------------------
let mut channels: Vec<OutputChannel> = Vec::new();
@@ -186,7 +196,7 @@ async fn main() {
}
// ---------------------------------------------------------------
- // 5. Find the requested device and start capture
+ // Find the requested device and start capture
// ---------------------------------------------------------------
let device_name = match &args.device_name {
Some(n) => n.as_str(),
@@ -224,7 +234,7 @@ async fn main() {
debug_log!("[dmvop] Capture started. Waiting for speech...");
// ---------------------------------------------------------------
- // 5. Event loop — listen for transcription & audio level events
+ // Event loop — listen for transcription & audio level events
// ---------------------------------------------------------------
let mut last_volume_db: f32 = -60.0;
diff --git a/src/output_protocol/ipc.rs b/src/output_protocol/ipc.rs
index fb6df80..ee27e42 100644
--- a/src/output_protocol/ipc.rs
+++ b/src/output_protocol/ipc.rs
@@ -60,8 +60,6 @@ impl OutputProtocol for IPCOutputProtocol {
debug_log!("[IPC] Connected to {}", self.socket_path.display());
let bytes = format!("{}\n", message);
let _ = stream.writable().await;
- // We can't use the stream directly here since we need to store it
- // for future sends. Let's store and send.
let _ = stream.try_write(bytes.as_bytes());
*guard = Some(stream);
}