feat: gui status handling if there is no remote server

This commit is contained in:
Ahmet Kaan Gümüş 2025-05-21 22:33:04 +03:00
parent 35ebb58698
commit 6efb12d3b0
3 changed files with 81 additions and 68 deletions

View file

@ -9,16 +9,22 @@ use s2n_quic::{
use tokio::{
io::{AsyncReadExt, AsyncWriteExt},
sync::{broadcast, oneshot},
task::JoinHandle,
};
use crate::{ClientConfig, SPEAKER_BUFFER_LENGHT, voice::play};
#[derive(Debug)]
pub struct ConnectReturn {
play_audio_stop_signal_sender: oneshot::Sender<bool>,
send_audio_task: JoinHandle<()>,
receive_audio_task: JoinHandle<()>,
}
pub async fn connect(
connection_stop_signal_receiver: oneshot::Receiver<bool>,
is_connection_started_signal: oneshot::Sender<bool>,
microphone_sender_for_producing_receiver: Arc<broadcast::Sender<f32>>,
microphone_receiver: broadcast::Receiver<f32>,
client_config: Arc<ClientConfig>,
) -> Result<(), Error> {
) -> Result<ConnectReturn, Error> {
let client = Client::builder()
.with_io("0:0")
.map_err(|err_val| Error::ConnectionSetup(err_val.to_string()))?
@ -50,52 +56,54 @@ pub async fn connect(
.open_bidirectional_stream()
.await
.map_err(|err_val| Error::ConnectionSetup(err_val.to_string()))?;
let (receive_stream, send_stream) = stream.split();
let (speaker_sender, speaker_receiver) = broadcast::channel(SPEAKER_BUFFER_LENGHT);
let (speaker_stop_signal_sender, speaker_stop_signal_receiver) = oneshot::channel();
tokio::spawn(play(speaker_receiver, speaker_stop_signal_receiver));
let receive_voice_data_task = tokio::spawn(receive_audio_data(receive_stream, speaker_sender));
let send_voice_data_task = tokio::spawn(send_audio_data(
send_stream,
microphone_sender_for_producing_receiver,
));
let (play_audio_stop_signal_sender, play_audio_stop_signal_receiver) = oneshot::channel();
if let Err(err_val) = is_connection_started_signal.send(true) {
eprintln!("Error: Is Connection Started | Local | Send | {}", err_val);
}
tokio::spawn(play(speaker_receiver, play_audio_stop_signal_receiver));
let receive_audio_task = tokio::spawn(receive_audio_data(receive_stream, speaker_sender));
let send_audio_task = tokio::spawn(send_audio_data(send_stream, microphone_receiver));
if let Err(err_val) = connection_stop_signal_receiver.await {
Ok(ConnectReturn {
play_audio_stop_signal_sender,
send_audio_task,
receive_audio_task,
})
}
pub async fn disconnect_watcher(
connection_stop_receiver: oneshot::Receiver<bool>,
connection_return: ConnectReturn,
) {
if let Err(err_val) = connection_stop_receiver.await {
eprintln!(
"Error: Connection Stop Signal | Local | Receive | {}",
"Error: Receive Connection Stop Signal | Local | {}",
err_val
);
}
if let Err(err_val) = speaker_stop_signal_sender.send(true) {
eprintln!("Error: Speaker Stop Signal | Local | Send | {}", err_val);
connection_return.send_audio_task.abort();
connection_return.receive_audio_task.abort();
if let Err(err_val) = connection_return.play_audio_stop_signal_sender.send(true) {
eprintln!("Error: Send Play Audio Stop Signal | Local | {}", err_val);
}
println!("Connection Is Closing");
receive_voice_data_task.abort();
send_voice_data_task.abort();
println!("Connection Is Closed");
Ok(())
}
async fn send_audio_data(
mut send_stream: SendStream,
microphone_sender_for_producing_receiver: Arc<broadcast::Sender<f32>>,
old_microphone_receiver: broadcast::Receiver<f32>,
) {
let mut microphone_receiver = microphone_sender_for_producing_receiver.subscribe();
let mut microphone_receiver = old_microphone_receiver.resubscribe();
drop(old_microphone_receiver);
loop {
match microphone_receiver.recv().await {
Ok(microphone_data) => {
if let Err(err_val) = send_stream.write_f32(microphone_data).await {
eprintln!("Error: Send Microphone Data | Remote | {}", err_val);
break;
todo!("GUI Status: Disconnect");
// break;
}
}
Err(err_val) => {
@ -117,6 +125,7 @@ async fn receive_audio_data(
loop {
match receive_stream.read_f32().await {
Ok(received_data) => {
// error only happens if there is no receiver, think about it
if let Err(err_val) = speaker_sender.send(received_data) {
eprintln!("Error: Send to Speaker | Local | {}", err_val);
break;
@ -124,7 +133,8 @@ async fn receive_audio_data(
}
Err(err_val) => {
eprintln!("Error: Receive Audio Data | Remote | {}", err_val);
break;
todo!("GUI Status Disconnect");
// break;
}
}
}