diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..c25e778 --- /dev/null +++ b/.gitignore @@ -0,0 +1,4 @@ +/target +/dist + +Cargo.lock diff --git a/Cargo.toml b/Cargo.toml new file mode 100644 index 0000000..7279077 --- /dev/null +++ b/Cargo.toml @@ -0,0 +1,22 @@ +[package] +name = "rust_communication" +version = "0.1.0" +edition = "2024" + +[dependencies] +console_error_panic_hook = "0.1.7" +leptos = { version = "0.7.8", features = ["csr"] } +wasm-bindgen-futures = "0.4.50" +web-sys = { version = "0.3.77", features = ["AudioBuffer", "AudioBufferSourceNode", "AudioContext", "HtmlAudioElement","MediaDevices", "MediaStream", "MediaStreamConstraints", "MediaStreamTrack", "Navigator", "Window"] } + +[profile] + +[profile.wasm-dev] +inherits = "dev" +opt-level = 1 + +[profile.server-dev] +inherits = "dev" + +[profile.android-dev] +inherits = "dev" diff --git a/index.html b/index.html new file mode 100644 index 0000000..dd7d8d2 --- /dev/null +++ b/index.html @@ -0,0 +1,6 @@ + + + +

"Hello"

+ + diff --git a/src/gui.rs b/src/gui.rs new file mode 100644 index 0000000..a75c8a8 --- /dev/null +++ b/src/gui.rs @@ -0,0 +1,58 @@ +use leptos::{ + IntoView, ev, + html::{ElementChild, button}, + logging::log, + prelude::{OnAttribute, Read, Show, ShowProps, ToChildren}, + server::LocalResource, + task::spawn_local, +}; +use wasm_bindgen_futures::JsFuture; +use web_sys::{ + HtmlAudioElement, MediaStream, MediaStreamConstraints, + wasm_bindgen::{JsCast, JsValue}, + window, +}; + +pub fn app() -> impl IntoView { + let audio_stream = LocalResource::new(|| media()); + let props = ShowProps::builder() + .when(move || audio_stream.read().is_some()) + .children(ToChildren::to_children(move || { + let audio_element = HtmlAudioElement::new().unwrap(); + let audio_stream = audio_stream.read(); + let audio_stream = audio_stream.as_deref(); + audio_element.set_src_object(audio_stream); + button() + .on(ev::click, move |_| match audio_element.play() { + Ok(audio_element_play_promise) => { + log!("{}", "Play will"); + spawn_local(async move { + JsFuture::from(audio_element_play_promise).await.ok(); + }); + log!("{}", "Play must"); + } + Err(err_val) => log!("{:#?}", err_val), + }) + .child("Happy Button") + .into_view() + })) + .fallback(|| button().child("Sad Button")) + .build(); + Show(props) +} + +async fn media() -> MediaStream { + let media_devices = window().unwrap().navigator().media_devices().unwrap(); + let constraints = MediaStreamConstraints::new(); + constraints.set_audio(&JsValue::TRUE); + let media_stream_promise = media_devices + .get_user_media_with_constraints(&constraints) + .unwrap(); + let media_stream = JsFuture::from(media_stream_promise) + .await + .unwrap() + .dyn_into::() + .unwrap(); + let audio_tracks = media_stream.get_audio_tracks(); + MediaStream::new_with_tracks(&audio_tracks).unwrap() +} diff --git a/src/lib.rs b/src/lib.rs new file mode 100644 index 0000000..14c39ab --- /dev/null +++ b/src/lib.rs @@ -0,0 +1 @@ +pub mod gui; diff --git a/src/main.rs b/src/main.rs new file mode 100644 index 0000000..8f1dd90 --- /dev/null +++ b/src/main.rs @@ -0,0 +1,9 @@ +use leptos::mount::mount_to_body; +use rust_communication::gui::app; + +fn main() { + println!("Hello, world!"); + + console_error_panic_hook::set_once(); + mount_to_body(app); +}