From bbb767cd20662656979110911b10a8e6d59c0a26 Mon Sep 17 00:00:00 2001 From: Gregor Klevze Date: Tue, 13 Jan 2026 13:18:46 +0100 Subject: [PATCH] build fix --- package-lock.json | 4 +-- src-tauri/Cargo.toml | 1 + src-tauri/src/lib.rs | 72 ++++++++++++++++++++++++++------------------ src/main.js | 15 +++++++++ 4 files changed, 61 insertions(+), 31 deletions(-) diff --git a/package-lock.json b/package-lock.json index 76920b2..e9d500e 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,12 +1,12 @@ { "name": "radio-tauri", - "version": "0.1.0", + "version": "0.1.1", "lockfileVersion": 3, "requires": true, "packages": { "": { "name": "radio-tauri", - "version": "0.1.0", + "version": "0.1.1", "devDependencies": { "@tauri-apps/cli": "^2", "cross-env": "^7.0.3", diff --git a/src-tauri/Cargo.toml b/src-tauri/Cargo.toml index 18b1da4..593fa2b 100644 --- a/src-tauri/Cargo.toml +++ b/src-tauri/Cargo.toml @@ -4,6 +4,7 @@ version = "0.1.1" description = "A Tauri App" authors = ["you"] edition = "2021" +default-run = "radio-tauri" # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html diff --git a/src-tauri/src/lib.rs b/src-tauri/src/lib.rs index 4e29973..bb1b147 100644 --- a/src-tauri/src/lib.rs +++ b/src-tauri/src/lib.rs @@ -3,7 +3,6 @@ use std::io::{BufRead, BufReader}; use std::net::{IpAddr, SocketAddr, TcpListener, TcpStream, UdpSocket}; use std::process::{Child, Command, Stdio}; use std::sync::Mutex; -use std::thread; use std::time::Duration; #[cfg(windows)] @@ -14,7 +13,7 @@ const CREATE_NO_WINDOW: u32 = 0x08000000; use mdns_sd::{ServiceDaemon, ServiceEvent}; use serde_json::json; -use tauri::{AppHandle, Manager, State}; +use tauri::{AppHandle, Manager, State, Emitter}; use tauri_plugin_shell::process::{CommandChild, CommandEvent}; use tauri_plugin_shell::ShellExt; use reqwest; @@ -560,40 +559,55 @@ pub fn run() { let controller = player::spawn_player_thread(shared); app.manage(PlayerRuntime { shared, controller }); + // Start mDNS discovery in background without blocking setup. + // This allows the main window to show immediately. let handle = app.handle().clone(); - thread::spawn(move || { - let mdns = ServiceDaemon::new().expect("Failed to create daemon"); - let receiver = mdns - .browse("_googlecast._tcp.local.") - .expect("Failed to browse"); - while let Ok(event) = receiver.recv() { - match event { - ServiceEvent::ServiceResolved(info) => { - let name = info - .get_property_val_str("fn") - .or_else(|| Some(info.get_fullname())) - .unwrap() - .to_string(); - let addresses = info.get_addresses(); - let ip = addresses - .iter() - .find(|ip| ip.is_ipv4()) - .or_else(|| addresses.iter().next()); + tauri::async_runtime::spawn(async move { + // Small delay to ensure window is fully initialized first. + tokio::time::sleep(Duration::from_millis(100)).await; + + std::thread::spawn(move || { + let mdns = ServiceDaemon::new().expect("Failed to create daemon"); + let receiver = mdns + .browse("_googlecast._tcp.local.") + .expect("Failed to browse"); + + while let Ok(event) = receiver.recv() { + match event { + ServiceEvent::ServiceResolved(info) => { + let name = info + .get_property_val_str("fn") + .or_else(|| Some(info.get_fullname())) + .unwrap() + .to_string(); + let addresses = info.get_addresses(); + let ip = addresses + .iter() + .find(|ip| ip.is_ipv4()) + .or_else(|| addresses.iter().next()); - if let Some(ip) = ip { - let state = handle.state::(); - let mut devices = state.known_devices.lock().unwrap(); - let ip_str = ip.to_string(); - if !devices.contains_key(&name) { - println!("Discovered Cast Device: {} at {}", name, ip_str); - devices.insert(name, ip_str); + if let Some(ip) = ip { + let state = handle.state::(); + let mut devices = state.known_devices.lock().unwrap(); + let ip_str = ip.to_string(); + if !devices.contains_key(&name) { + println!("Discovered Cast Device: {} at {}", name, ip_str); + devices.insert(name.clone(), ip_str.clone()); + + // Emit event to frontend when new device is discovered. + let _ = handle.emit("cast-device-discovered", json!({ + "name": name, + "ip": ip_str + })); + } } } + _ => {} } - _ => {} } - } + }); }); + Ok(()) }) .invoke_handler(tauri::generate_handler![ diff --git a/src/main.js b/src/main.js index ba8146e..5e99e9b 100644 --- a/src/main.js +++ b/src/main.js @@ -1050,6 +1050,17 @@ function setupEventListeners() { await appWindow.close(); }); + // Listen for cast device discovery events from backend + if (runningInTauri && window.__TAURI__ && window.__TAURI__.event) { + window.__TAURI__.event.listen('cast-device-discovered', (event) => { + console.log('Cast device discovered:', event.payload); + // If cast overlay is currently open, refresh the device list + if (!castOverlay.classList.contains('hidden')) { + refreshCastDeviceList(); + } + }); + } + // Menu button - explicit functionality or placeholder? // Menu removed — header click opens stations via artwork placeholder @@ -1353,6 +1364,10 @@ async function openCastOverlay() { castOverlay.setAttribute('aria-hidden', 'false'); // ensure cast overlay shows linear list style deviceListEl.classList.remove('stations-grid'); + await refreshCastDeviceList(); +} + +async function refreshCastDeviceList() { deviceListEl.innerHTML = '
  • Scanning...
    Searching for speakers
  • '; try {