gosuto_livekit/room/track/
local_audio_track.rs1use core::panic;
16use std::{fmt::Debug, sync::Arc};
17
18use gosuto_libwebrtc::{prelude::*, stats::RtcStats};
19use livekit_protocol as proto;
20
21use super::TrackInner;
22use crate::{prelude::*, rtc_engine::lk_runtime::LkRuntime};
23
24#[derive(Clone)]
25pub struct LocalAudioTrack {
26 inner: Arc<TrackInner>,
27 source: RtcAudioSource,
28}
29
30impl Debug for LocalAudioTrack {
31 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
32 f.debug_struct("LocalAudioTrack")
33 .field("sid", &self.sid())
34 .field("name", &self.name())
35 .field("source", &self.source())
36 .finish()
37 }
38}
39
40impl LocalAudioTrack {
41 pub(crate) fn new(name: String, rtc_track: RtcAudioTrack, source: RtcAudioSource) -> Self {
42 Self {
43 inner: Arc::new(super::new_inner(
44 "TR_unknown".to_owned().try_into().unwrap(),
45 name,
46 TrackKind::Audio,
47 MediaStreamTrack::Audio(rtc_track),
48 )),
49 source,
50 }
51 }
52
53 pub fn create_audio_track(name: &str, source: RtcAudioSource) -> LocalAudioTrack {
54 let rtc_track = match source.clone() {
55 #[cfg(not(target_arch = "wasm32"))]
56 RtcAudioSource::Native(native_source) => {
57 use gosuto_libwebrtc::peer_connection_factory::native::PeerConnectionFactoryExt;
58 LkRuntime::instance()
59 .pc_factory()
60 .create_audio_track(&gosuto_libwebrtc::native::create_random_uuid(), native_source)
61 }
62 _ => panic!("unsupported audio source"),
63 };
64 Self::new(name.to_string(), rtc_track, source)
65 }
66
67 pub fn sid(&self) -> TrackSid {
68 self.inner.info.read().sid.clone()
69 }
70
71 pub fn name(&self) -> String {
72 self.inner.info.read().name.clone()
73 }
74
75 pub fn kind(&self) -> TrackKind {
76 self.inner.info.read().kind
77 }
78
79 pub fn source(&self) -> TrackSource {
80 self.inner.info.read().source
81 }
82
83 pub fn stream_state(&self) -> StreamState {
84 self.inner.info.read().stream_state
85 }
86
87 pub fn is_enabled(&self) -> bool {
88 self.inner.rtc_track.enabled()
89 }
90
91 pub fn enable(&self) {
92 self.inner.rtc_track.set_enabled(true);
93 }
94
95 pub fn disable(&self) {
96 self.inner.rtc_track.set_enabled(false);
97 }
98
99 pub fn is_muted(&self) -> bool {
100 self.inner.info.read().muted
101 }
102
103 pub fn mute(&self) {
104 super::set_muted(&self.inner, &Track::LocalAudio(self.clone()), true);
105 }
106
107 pub fn unmute(&self) {
108 super::set_muted(&self.inner, &Track::LocalAudio(self.clone()), false);
109 }
110
111 pub fn rtc_track(&self) -> RtcAudioTrack {
112 if let MediaStreamTrack::Audio(audio) = self.inner.rtc_track.clone() {
113 return audio;
114 }
115 unreachable!();
116 }
117
118 pub fn rtc_source(&self) -> RtcAudioSource {
119 self.source.clone()
120 }
121
122 pub fn is_remote(&self) -> bool {
123 false
124 }
125
126 pub async fn get_stats(&self) -> RoomResult<Vec<RtcStats>> {
127 super::local_track::get_stats(&self.inner).await
128 }
129
130 pub(crate) fn on_muted(&self, f: impl Fn(Track) + Send + 'static) {
131 self.inner.events.lock().muted.replace(Box::new(f));
132 }
133
134 pub(crate) fn on_unmuted(&self, f: impl Fn(Track) + Send + 'static) {
135 self.inner.events.lock().unmuted.replace(Box::new(f));
136 }
137
138 pub(crate) fn transceiver(&self) -> Option<RtpTransceiver> {
139 self.inner.info.read().transceiver.clone()
140 }
141
142 pub(crate) fn set_transceiver(&self, transceiver: Option<RtpTransceiver>) {
143 self.inner.info.write().transceiver = transceiver;
144 }
145
146 pub(crate) fn update_info(&self, info: proto::TrackInfo) {
147 super::update_info(&self.inner, &Track::LocalAudio(self.clone()), info);
148 }
149}