]> code.octet-stream.net Git - m17rt/blobdiff - m17codec2/src/tx.rs
Make netclient work against mrefd
[m17rt] / m17codec2 / src / tx.rs
index c0eb5968fcdd31217ba3dbac6fec5ee0019ed1fe..d9028fb7f5267ae1a56befa8eb10ec31d747514f 100644 (file)
@@ -1,24 +1,24 @@
 use codec2::{Codec2, Codec2Mode};
 use codec2::{Codec2, Codec2Mode};
+use cpal::SampleFormat;
+use cpal::SampleRate;
 use cpal::traits::DeviceTrait;
 use cpal::traits::HostTrait;
 use cpal::traits::StreamTrait;
 use cpal::traits::DeviceTrait;
 use cpal::traits::HostTrait;
 use cpal::traits::StreamTrait;
-use cpal::SampleFormat;
-use cpal::SampleRate;
 use log::debug;
 use log::debug;
+use m17app::StreamFrame;
 use m17app::adapter::StreamAdapter;
 use m17app::app::TxHandle;
 use m17app::error::AdapterError;
 use m17app::link_setup::LinkSetup;
 use m17app::link_setup::M17Address;
 use m17app::adapter::StreamAdapter;
 use m17app::app::TxHandle;
 use m17app::error::AdapterError;
 use m17app::link_setup::LinkSetup;
 use m17app::link_setup::M17Address;
-use m17app::StreamFrame;
 use rubato::Resampler;
 use rubato::SincFixedOut;
 use rubato::SincInterpolationParameters;
 use std::path::PathBuf;
 use rubato::Resampler;
 use rubato::SincFixedOut;
 use rubato::SincInterpolationParameters;
 use std::path::PathBuf;
-use std::sync::mpsc;
-use std::sync::mpsc::channel;
 use std::sync::Arc;
 use std::sync::Mutex;
 use std::sync::Arc;
 use std::sync::Mutex;
+use std::sync::mpsc;
+use std::sync::mpsc::channel;
 use std::time::Duration;
 use std::time::Instant;
 
 use std::time::Duration;
 use std::time::Instant;
 
@@ -134,6 +134,33 @@ impl Codec2TxAdapter {
             tx: self.event_tx.clone(),
         }
     }
             tx: self.event_tx.clone(),
         }
     }
+
+    /// List sound cards supported for audio input.
+    ///
+    /// M17RT will handle any card with 1 or 2 channels and 16-bit output.
+    pub fn supported_input_cards() -> Vec<String> {
+        let mut out = vec![];
+        let host = cpal::default_host();
+        let Ok(input_devices) = host.input_devices() else {
+            return out;
+        };
+        for d in input_devices {
+            let Ok(mut configs) = d.supported_input_configs() else {
+                continue;
+            };
+            if configs.any(|config| {
+                (config.channels() == 1 || config.channels() == 2)
+                    && config.sample_format() == SampleFormat::I16
+            }) {
+                let Ok(name) = d.name() else {
+                    continue;
+                };
+                out.push(name);
+            }
+        }
+        out.sort();
+        out
+    }
 }
 
 enum Event {
 }
 
 enum Event {