aboutsummaryrefslogtreecommitdiff
path: root/examples
diff options
context:
space:
mode:
Diffstat (limited to 'examples')
-rw-r--r--examples/nrf/src/bin/i2s_waveform.rs (renamed from examples/nrf/src/bin/i2s-generate.rs)103
1 files changed, 61 insertions, 42 deletions
diff --git a/examples/nrf/src/bin/i2s-generate.rs b/examples/nrf/src/bin/i2s_waveform.rs
index c2b5578f3..81858ff59 100644
--- a/examples/nrf/src/bin/i2s-generate.rs
+++ b/examples/nrf/src/bin/i2s_waveform.rs
@@ -6,33 +6,29 @@ use core::f32::consts::PI;
6 6
7use defmt::{error, info}; 7use defmt::{error, info};
8use embassy_executor::Spawner; 8use embassy_executor::Spawner;
9use embassy_nrf::i2s::{self, Sample as _}; 9use embassy_nrf::i2s::{self, Channels, Config, MasterClock, Sample as _, SampleWidth, I2S};
10use embassy_nrf::interrupt; 10use embassy_nrf::interrupt;
11use {defmt_rtt as _, panic_probe as _}; 11use {defmt_rtt as _, panic_probe as _};
12 12
13type Sample = i16;
14
15const NUM_SAMPLES: usize = 6000;
16
13#[embassy_executor::main] 17#[embassy_executor::main]
14async fn main(_spawner: Spawner) { 18async fn main(_spawner: Spawner) {
15 let p = embassy_nrf::init(Default::default()); 19 let p = embassy_nrf::init(Default::default());
16 20
17 let mut config = i2s::Config::default(); 21 let master_clock: MasterClock = i2s::ExactSampleRate::_50000.into();
18 config.mode = i2s::ExactSampleRate::_50000.into();
19 config.channels = i2s::Channels::Left;
20 config.swidth = i2s::SampleWidth::_16bit;
21 let sample_rate = config.mode.sample_rate().expect("I2S Master");
22 let inv_sample_rate = 1.0 / sample_rate as f32;
23 22
23 let sample_rate = master_clock.sample_rate();
24 info!("Sample rate: {}", sample_rate); 24 info!("Sample rate: {}", sample_rate);
25 25
26 // Wait for a button press 26 let config = Config::default()
27 // use embassy_nrf::gpio::{Input, Pin, Pull}; 27 .sample_width(SampleWidth::_16bit)
28 // let mut btn1 = Input::new(p.P1_00.degrade(), Pull::Up); 28 .channels(Channels::MonoLeft);
29 // btn1.wait_for_low().await;
30 29
31 let irq = interrupt::take!(I2S); 30 let irq = interrupt::take!(I2S);
32 let mut i2s = i2s::I2S::new(p.I2S, irq, p.P0_28, p.P0_29, p.P0_31, p.P0_27, p.P0_30, config).output(); 31 let mut output_stream = I2S::master(p.I2S, irq, p.P0_25, p.P0_26, p.P0_27, master_clock, config).output(p.P0_28);
33
34 type Sample = i16;
35 const NUM_SAMPLES: usize = 6000;
36 32
37 let mut buffers: [i2s::AlignedBuffer<Sample, NUM_SAMPLES>; 3] = [ 33 let mut buffers: [i2s::AlignedBuffer<Sample, NUM_SAMPLES>; 3] = [
38 i2s::AlignedBuffer::default(), 34 i2s::AlignedBuffer::default(),
@@ -40,36 +36,16 @@ async fn main(_spawner: Spawner) {
40 i2s::AlignedBuffer::default(), 36 i2s::AlignedBuffer::default(),
41 ]; 37 ];
42 38
43 let mut carrier = SineOsc::new(); 39 let mut waveform = Waveform::new(1.0 / sample_rate as f32);
44
45 let mut freq_mod = SineOsc::new();
46 freq_mod.set_frequency(8.0, inv_sample_rate);
47 freq_mod.set_amplitude(1.0);
48
49 let mut amp_mod = SineOsc::new();
50 amp_mod.set_frequency(16.0, inv_sample_rate);
51 amp_mod.set_amplitude(0.5);
52
53 let mut generate = |buf: &mut [Sample]| {
54 for sample in &mut buf.chunks_mut(1) {
55 let freq_modulation = bipolar_to_unipolar(freq_mod.generate());
56 carrier.set_frequency(220.0 + 440.0 * freq_modulation, inv_sample_rate);
57 let amp_modulation = bipolar_to_unipolar(amp_mod.generate());
58 carrier.set_amplitude(amp_modulation);
59 let signal = carrier.generate();
60 let value = (Sample::SCALE as f32 * signal) as Sample;
61 sample[0] = value;
62 }
63 };
64 40
65 generate(buffers[0].as_mut()); 41 waveform.process(&mut buffers[0]);
66 generate(buffers[1].as_mut()); 42 waveform.process(&mut buffers[1]);
67 43
68 i2s.start(buffers[0].as_ref()).await.expect("I2S Start"); 44 output_stream.start(&buffers[0]).await.expect("I2S Start");
69 45
70 let mut index = 1; 46 let mut index = 1;
71 loop { 47 loop {
72 if let Err(err) = i2s.send(buffers[index].as_ref()).await { 48 if let Err(err) = output_stream.send_from_ram(&buffers[index]).await {
73 error!("{}", err); 49 error!("{}", err);
74 } 50 }
75 51
@@ -77,11 +53,54 @@ async fn main(_spawner: Spawner) {
77 if index >= 3 { 53 if index >= 3 {
78 index = 0; 54 index = 0;
79 } 55 }
80 generate(buffers[index].as_mut()); 56
57 waveform.process(&mut buffers[index]);
58 }
59}
60
61struct Waveform {
62 inv_sample_rate: f32,
63 carrier: SineOsc,
64 freq_mod: SineOsc,
65 amp_mod: SineOsc,
66}
67
68impl Waveform {
69 fn new(inv_sample_rate: f32) -> Self {
70 let carrier = SineOsc::new();
71
72 let mut freq_mod = SineOsc::new();
73 freq_mod.set_frequency(8.0, inv_sample_rate);
74 freq_mod.set_amplitude(1.0);
75
76 let mut amp_mod = SineOsc::new();
77 amp_mod.set_frequency(16.0, inv_sample_rate);
78 amp_mod.set_amplitude(0.5);
79
80 Self {
81 inv_sample_rate,
82 carrier,
83 freq_mod,
84 amp_mod,
85 }
86 }
87
88 fn process(&mut self, buf: &mut [Sample]) {
89 for sample in buf.chunks_mut(1) {
90 let freq_modulation = bipolar_to_unipolar(self.freq_mod.generate());
91 self.carrier
92 .set_frequency(110.0 + 440.0 * freq_modulation, self.inv_sample_rate);
93
94 let amp_modulation = bipolar_to_unipolar(self.amp_mod.generate());
95 self.carrier.set_amplitude(amp_modulation);
96
97 let signal = self.carrier.generate();
98
99 sample[0] = (Sample::SCALE as f32 * signal) as Sample;
100 }
81 } 101 }
82} 102}
83 103
84#[derive(Clone)]
85struct SineOsc { 104struct SineOsc {
86 amplitude: f32, 105 amplitude: f32,
87 modulo: f32, 106 modulo: f32,