@@ -24,7 +24,22 @@ There are three different kinds of audio sources that can be played using the
24
24
my_effect = audio.SoundEffect(freq_start=400, freq_end=2500, duration=500)
25
25
audio.play(my_effect)
26
26
27
- 3. `Audio Frames <#audioframe >`_, an instance or an iterable (like a list or
27
+ 3. `Audio Recordings <#audiorecording-audiotrack-v2 >`_, a way to record audio
28
+ data from the microphone::
29
+
30
+ recording = audio.AudioRecording(duration=4000)
31
+ microphone.record(recording)
32
+ audio.play(recording)
33
+
34
+ 4. `Audio Tracks <#audiorecording-audiotrack-v2 >`_, a way to point to a portion
35
+ of the data in an ``AudioRecording `` or a ``bytearray `` and/or modify it::
36
+
37
+ recording = audio.AudioRecording(duration=4000)
38
+ microphone.record(recording)
39
+ track = AudioTrack(recording)[1000:2000]
40
+ audio.play(track)
41
+
42
+ 5. `Audio Frames <#audioframe >`_, an instance or an iterable (like a list or
28
43
generator) of Audio Frames, which are lists of samples with values
29
44
from 0 to 255::
30
45
@@ -49,6 +64,12 @@ Functions
49
64
be found in the `Built in sounds <#built-in-sounds-v2 >`_ section.
50
65
- ``SoundEffect ``: A sound effect, or an iterable of sound effects,
51
66
created via the :py:meth: `audio.SoundEffect ` class
67
+ - ``AudioRecording ``: An instance or an iterable of ``AudioRecording ``
68
+ instances as described in the
69
+ `AudioRecording Technical Details <#technical-details >`_ section
70
+ - ``AudioTrack ``: An instance or an iterable of ``AudioTrack ``
71
+ instances as described in the
72
+ `AudioTrack Technical Details <#technical-details >`_ section
52
73
- ``AudioFrame ``: An instance or an iterable of ``AudioFrame ``
53
74
instances as described in the
54
75
`AudioFrame Technical Details <#technical-details >`_ section
@@ -226,47 +247,150 @@ Sound Effects Example
226
247
:code: python
227
248
228
249
229
- AudioFrame
230
- ==========
250
+ AudioRecording & AudioTrack ** V2 **
251
+ ==================================
231
252
232
- .. py :class ::
233
- AudioFrame(duration=-1, rate=7812)
253
+ There are two classes that contain audio data with an associated sampling rate:
234
254
235
- An ``AudioFrame `` object is a list of samples, each of which is an unsigned
236
- byte (whole number between 0 and 255).
255
+ - ``AudioRecording `` contains its own buffer, it's initialised with a size
256
+ defined in time, and it's the object type that ``microphone.record() ``
257
+ returns.
258
+ - ``AudioTrack `` does not hold its own buffer and instead points to a buffer
259
+ externally created. This buffer could be an ``AudioRecording ``, or a basic
260
+ type like a ``bytearray ``. It's similar to a
261
+ `memoryview <https://docs.micropython.org/en/v1.9.3/pyboard/reference/speed_python.html#arrays >`_
262
+ and it can be used to easily chop a portion of the audio data in the
263
+ ``AudioRecording ``.
237
264
238
- The number of samples in an AudioFrame will depend on the
239
- ``rate `` (number of samples per second) and ``duration `` parameters.
240
- The total number of samples will always be a round up multiple of 32.
265
+ AudioRecording
266
+ --------------
241
267
242
- On micro:bit V1 the constructor does not take any arguments,
243
- and an AudioFrame instance is always 32 bytes.
268
+ .. py : class ::
269
+ AudioRecording(duration, rate=7812)
244
270
245
- :param duration: (**V2 **) Indicates how many milliseconds of audio this
271
+ The ``AudioRecording `` object contains audio data and the sampling rate
272
+ associated to it.
273
+
274
+ The size of the internal buffer will depend on the ``rate ``
275
+ (number of samples per second) and ``duration `` parameters.
276
+
277
+ :param duration: Indicates how many milliseconds of audio this
246
278
instance can store.
247
- :param rate: (** V2 **) The sampling rate at which data will be stored
279
+ :param rate: The sampling rate at which data will be stored
248
280
via the microphone, or played via the ``audio.play() `` function.
249
281
250
282
.. py :function :: set_rate(sample_rate)
251
283
252
- (**V2 only **) Configure the sampling rate associated with the data
253
- in the ``AudioFrame `` instance.
284
+ Configure the sampling rate associated with the data in the
285
+ ``AudioRecording `` instance.
286
+
287
+ :param sample_rate: The sample rate to set.
288
+
289
+ .. py :function :: get_rate()
290
+
291
+ Return the configured sampling rate for this
292
+ ``AudioRecording `` instance.
293
+
294
+ :return: The configured sample rate.
295
+
296
+ .. py :function :: track(start_ms = 0 , end_ms = - 1 )
297
+
298
+ Create an `AudioTrack <#audio.AudioTrack >`_ instance from a portion of
299
+ the data in this ``AudioRecording `` instance.
300
+
301
+ :param start_ms: Where to start of the track in milliseconds.
302
+ :param end_ms: The end of the track in milliseconds.
303
+ If the default value of ``-1 `` is provided it will end the track
304
+ at the end of the AudioRecording.
305
+
306
+ When an AudioRecording is used to record data from the microphone,
307
+ increasing the sampling rate increases the sound quality,
308
+ but it also increases the amount of memory used.
309
+
310
+ During playback, increasing the sampling rate speeds up the sound
311
+ and decreasing the sample rate slows it down.
312
+
313
+ AudioTrack
314
+ ----------
315
+
316
+ ``AudioTrack `` individual bytes can be accessed like an element in a list
317
+
318
+ .. py :class ::
319
+ AudioTrack(buffer, rate=7812)
320
+
321
+ The ``AudioTrack `` object is a ``memoryview `` of an audio buffer,
322
+ like ``AudioRecording `` or ``bytearray ``, which also contains its own
323
+ sampling rate.
324
+
325
+ :param buffer: The buffer containing the audio data.
326
+ :param rate: The sampling rate at which data will be stored
327
+ via the microphone, or played via the ``audio.play() `` function.
254
328
255
- For recording from the microphone, increasing the sampling rate
256
- increases the sound quality, but reduces the length of audio it
257
- can store.
258
- During playback, increasing the sampling rate speeds up the sound
259
- and decreasing it slows it down.
329
+ .. py :function :: set_rate(sample_rate)
330
+
331
+ Configure the sampling rate associated with the data in the
332
+ ``AudioTrack `` instance.
260
333
261
334
:param sample_rate: The sample rate to set.
262
335
263
336
.. py :function :: get_rate()
264
337
265
- (** V2 only **) Return the configured sampling rate for this
266
- ``AudioFrame `` instance.
338
+ Return the configured sampling rate for this
339
+ ``AudioTrack `` instance.
267
340
268
341
:return: The configured sample rate.
269
342
343
+ .. py :function :: copyfrom(other)
344
+
345
+ Overwrite the data in this ``AudioTrack `` with the data from another
346
+ ``AudioTrack ``, ``AudioRecording `` or buffer-like object like
347
+ a ``bytes `` or ``bytearray `` instance.
348
+
349
+ :param other: Buffer-like instance from which to copy the data.
350
+
351
+ Example
352
+ -------
353
+
354
+ ::
355
+
356
+ from microbit import *
357
+
358
+ # An AudioRecording holds the audio data
359
+ recording = audio.AudioRecording(duration=4000)
360
+
361
+ # AudioTracks point to a portion of the data in the AudioRecording
362
+ # We can obtain the an AudioTrack from the AudioRecording.track() method
363
+ first_half = recording.track(end_ms=2000)
364
+ # Or we can create an AudioTrack from an AudioRecording and slice it
365
+ full_track = audio.AudioTrack(recording)
366
+ second_half = full_track[full_track.length() // 2:]
367
+
368
+ while True:
369
+ if button_a.is_pressed():
370
+ # We can record directly inside the AudioRecording
371
+ microphone.record(recording)
372
+ if button_b.is_pressed():
373
+ audio.play(recording, wait=False)
374
+ # The rate can be changed while playing
375
+ first_half.set_rate(
376
+ scale(accelerometer.get_x(), from_=(-1000, 1000), to=(3_000, 30_000))
377
+ )
378
+ if pin_logo.is_touched():
379
+ # We can also play the AudioTrack pointing to the AudioRecording
380
+ audio.play(first_half)
381
+
382
+
383
+ AudioFrame
384
+ ==========
385
+
386
+ .. py :class ::
387
+ AudioFrame
388
+
389
+ An ``AudioFrame `` object is a list of 32 samples each of which is an unsigned byte
390
+ (whole number between 0 and 255).
391
+
392
+ It takes just over 4 ms to play a single frame.
393
+
270
394
.. py :function :: copyfrom(other)
271
395
272
396
Overwrite the data in this ``AudioFrame `` with the data from another
@@ -281,21 +405,14 @@ Technical Details
281
405
You don't need to understand this section to use the ``audio `` module.
282
406
It is just here in case you wanted to know how it works.
283
407
284
- The ``audio.play() `` function can consume an instance or iterable
285
- (sequence, like list or tuple, or generator) of ``AudioFrame `` instances,
286
- The ``AudioFrame `` default playback rate is 7812 Hz, and can be configured
287
- at any point with the ``AudioFrame.set_rate() `` method.
288
- The ``AudioFrame.set_rate() `` also works while the ``AudioFrame `` is being
289
- played, which will affect the playback speed.
290
-
291
- Each ``AudioFrame `` instance is 32 samples by default, but it can be
292
- configured to a different size via constructor parameters.
408
+ The ``audio `` module can consumes an iterable (sequence, like list or tuple, or
409
+ generator) of ``AudioFrame `` instances, each 32 samples at 7812.5 Hz.
293
410
294
- So, for example, playing 32 samples at 7812 Hz takes just over 4 milliseconds
411
+ So, for example, playing 32 samples at 7812.5 Hz takes just over 4 milliseconds
295
412
(1/7812.5 * 32 = 0.004096 = 4096 microseconds).
296
413
297
- The function ``play() `` fully copies all data from each ``AudioFrame `` before
298
- it calls ``next() `` for the next frame, so a sound source can use the same
414
+ The function ``play `` fully copies all data from each ``AudioFrame `` before it
415
+ calls ``next() `` for the next frame, so a sound source can use the same
299
416
``AudioFrame `` repeatedly.
300
417
301
418
The ``audio `` module has an internal 64 sample buffer from which it reads
0 commit comments