Always emit quality format updates with fallbacks

Send file/device audio-quality notifications even when stream metadata is incomplete by deriving sane defaults from the requested quality level, so controller quality icons stay in sync.
This commit is contained in:
joren
2026-03-31 23:33:56 +02:00
parent c3cad15719
commit 20d5ecf231

View File

@@ -418,6 +418,16 @@ fn msg_device_audio_quality_changed(
build_qconnect_message(27, &payload) build_qconnect_message(27, &payload)
} }
fn quality_fallback_audio_params(quality: u32) -> (u32, u32, u32) {
match quality {
1 => (44100, 16, 2), // MP3
2 => (44100, 16, 2), // CD
3 => (96000, 24, 2), // Hi-Res up to 96kHz
4 | 5 => (192000, 24, 2), // Hi-Res up to 192/384kHz (use 192kHz fallback)
_ => (44100, 16, 2),
}
}
/// RNDR_SRVR_VOLUME_MUTED (29): renderer confirms mute state. /// RNDR_SRVR_VOLUME_MUTED (29): renderer confirms mute state.
fn msg_volume_muted(muted: bool) -> Vec<u8> { fn msg_volume_muted(muted: bool) -> Vec<u8> {
let payload = encode_field_varint(1, if muted { 1 } else { 0 }); let payload = encode_field_varint(1, if muted { 1 } else { 0 });
@@ -1117,24 +1127,26 @@ async fn run_connection(
duration_ms, duration_ms,
start_position_ms: requested_pos.unwrap_or(0), start_position_ms: requested_pos.unwrap_or(0),
}); });
if let (Some(sr), Some(bits)) = (stream_sr, stream_bits) { let (fallback_sr, fallback_bits, fallback_ch) =
let ch = stream_ch.unwrap_or(2).max(1); quality_fallback_audio_params(max_audio_quality);
let file_msg = msg_file_audio_quality_changed( let sr = stream_sr.unwrap_or(fallback_sr).max(1);
sr as u64, let bits = stream_bits.unwrap_or(fallback_bits).max(1);
bits as u64, let ch = stream_ch.unwrap_or(fallback_ch).max(1);
ch as u64, let file_msg = msg_file_audio_quality_changed(
max_audio_quality as u64, sr as u64,
); bits as u64,
ws_tx.send(Message::Binary(build_payload_frame(msg_id, &file_msg).into())).await?; ch as u64,
msg_id += 1; max_audio_quality as u64,
let dev_msg = msg_device_audio_quality_changed( );
sr as u64, ws_tx.send(Message::Binary(build_payload_frame(msg_id, &file_msg).into())).await?;
bits as u64, msg_id += 1;
ch as u64, let dev_msg = msg_device_audio_quality_changed(
); sr as u64,
ws_tx.send(Message::Binary(build_payload_frame(msg_id, &dev_msg).into())).await?; bits as u64,
msg_id += 1; ch as u64,
} );
ws_tx.send(Message::Binary(build_payload_frame(msg_id, &dev_msg).into())).await?;
msg_id += 1;
current_buffer_state = 2; // OK current_buffer_state = 2; // OK
} }
Err(e) => { Err(e) => {
@@ -1374,24 +1386,26 @@ async fn run_connection(
duration_ms, duration_ms,
start_position_ms: 0, start_position_ms: 0,
}); });
if let (Some(sr), Some(bits)) = (stream_sr, stream_bits) { let (fallback_sr, fallback_bits, fallback_ch) =
let ch = stream_ch.unwrap_or(2).max(1); quality_fallback_audio_params(*quality);
let file_msg = msg_file_audio_quality_changed( let sr = stream_sr.unwrap_or(fallback_sr).max(1);
sr as u64, let bits = stream_bits.unwrap_or(fallback_bits).max(1);
bits as u64, let ch = stream_ch.unwrap_or(fallback_ch).max(1);
ch as u64, let file_msg = msg_file_audio_quality_changed(
*quality as u64, sr as u64,
); bits as u64,
ws_tx.send(Message::Binary(build_payload_frame(msg_id, &file_msg).into())).await?; ch as u64,
msg_id += 1; *quality as u64,
let dev_msg = msg_device_audio_quality_changed( );
sr as u64, ws_tx.send(Message::Binary(build_payload_frame(msg_id, &file_msg).into())).await?;
bits as u64, msg_id += 1;
ch as u64, let dev_msg = msg_device_audio_quality_changed(
); sr as u64,
ws_tx.send(Message::Binary(build_payload_frame(msg_id, &dev_msg).into())).await?; bits as u64,
msg_id += 1; ch as u64,
} );
ws_tx.send(Message::Binary(build_payload_frame(msg_id, &dev_msg).into())).await?;
msg_id += 1;
// Re-emit quality confirmation after successful restart // Re-emit quality confirmation after successful restart
// so controllers observing the currently active stream update promptly. // so controllers observing the currently active stream update promptly.
let confirm = msg_max_audio_quality_changed(*quality as u64, None); let confirm = msg_max_audio_quality_changed(*quality as u64, None);