Record sound: Difference between revisions

From Rosetta Code
Content added Content deleted
(sort)
 
(11 intermediate revisions by 5 users not shown)
Line 21: Line 21:


=={{header|AutoHotkey}}==
=={{header|AutoHotkey}}==
<lang autohotkey>name := "sample"
<syntaxhighlight lang="autohotkey">name := "sample"
waitsec := 5
waitsec := 5
Tooltip Recording %name%.wav
Tooltip Recording %name%.wav
Line 56: Line 56:
; For more intuitive functions, see the MCI library by jballi.
; For more intuitive functions, see the MCI library by jballi.
; doc: http://www.autohotkey.net/~jballi/MCI/v1.1/MCI.html
; doc: http://www.autohotkey.net/~jballi/MCI/v1.1/MCI.html
; download: http://www.autohotkey.net/~jballi/MCI/v1.1/MCI.ahk</lang>
; download: http://www.autohotkey.net/~jballi/MCI/v1.1/MCI.ahk</syntaxhighlight>


=={{header|BBC BASIC}}==
=={{header|BBC BASIC}}==
{{works with|BBC BASIC for Windows}}
{{works with|BBC BASIC for Windows}}
<lang bbcbasic> wavfile$ = @dir$ + "capture.wav"
<syntaxhighlight lang="bbcbasic"> wavfile$ = @dir$ + "capture.wav"
bitspersample% = 16
bitspersample% = 16
channels% = 2
channels% = 2
Line 95: Line 95:
SYS "mciSendString", "close capture", 0, 0, 0
SYS "mciSendString", "close capture", 0, 0, 0
PRINT "Captured audio is stored in " wavfile$</lang>
PRINT "Captured audio is stored in " wavfile$</syntaxhighlight>


{{omit from|Batch File}}
{{omit from|Batch File}}
Line 103: Line 103:
Read/write raw device <code>/dev/dsp</code>. On Linux you need access to said device, meaning probably you should be in audio user group.
Read/write raw device <code>/dev/dsp</code>. On Linux you need access to said device, meaning probably you should be in audio user group.


<lang c>#include <stdlib.h>
<syntaxhighlight lang="c">#include <stdlib.h>
#include <unistd.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/types.h>
Line 132: Line 132:
play(p, 65536);
play(p, 65536);
return 0;
return 0;
}</lang>
}</syntaxhighlight>


=={{header|C++}}==
=={{header|C++}}==
Uses Windows MCI
Uses Windows MCI
<lang cpp>
<syntaxhighlight lang="cpp">
#include <iostream>
#include <iostream>
#include <string>
#include <string>
Line 230: Line 230:
return 0;
return 0;
}
}
</syntaxhighlight>
</lang>


=={{header|ChucK}}==
=={{header|ChucK}}==


<lang c>// chuck this with other shreds to record to file
<syntaxhighlight lang="c">// chuck this with other shreds to record to file
// example> chuck foo.ck bar.ck rec
// example> chuck foo.ck bar.ck rec


Line 256: Line 256:
// infinite time loop...
// infinite time loop...
// ctrl-c will stop it, or modify to desired duration
// ctrl-c will stop it, or modify to desired duration
while( true ) 1::second => now;</lang>
while( true ) 1::second => now;</syntaxhighlight>


=={{header|Common Lisp}}==
=={{header|Common Lisp}}==
{{trans|C}}
{{trans|C}}
<lang lisp>
<syntaxhighlight lang="lisp">
(defun record (n)
(defun record (n)
(with-open-file (in "/dev/dsp" :element-type '(unsigned-byte 8))
(with-open-file (in "/dev/dsp" :element-type '(unsigned-byte 8))
Line 272: Line 272:
)
)
(play (record 65536))
(play (record 65536))
</syntaxhighlight>
</lang>

=={{header|Diego}}==
This <code>funct</code>ion returns a <code>{wav}</code> variable recorded from a thing in the mist. It understands that the found <code>thing</code> has a microphone, so will have microphone knowledge. If the caller does not have microphone knowledge, the callee will train the caller on first request.
<syntaxhighlight lang="diego">begin_funct({wav}, Record sound);
set_decision(linger);
find_thing()_first()_microphone()_bitrate(16)_tech(PCM)_samplerate(signed16, unsigned16)_rangefrom(8000, Hz)_rangeto(44100, Hz)_export(.wav)
? with_found()_microphone()_label(mic);
: err_funct[]_err(Sorry, no one has a microphone!);
exit_funct[];
;
with_microphone[mic]_record()_durat({secs}, 30)_var(recording);
[Record sound]_ret([recording]);
reset_decision();
end_funct[];

// Record a monophonic 16-bit PCM sound into memory space:
exec_funct(Record sound)_var(PCMRecording)_me(); // The variable 'PCMRecording' is the sound in memory space

// Record a monophonic 16-bit PCM sound into a file or array:
exec_funct(Record sound)_file(foo.wav)_me(); // The file 'foo.wav' is the sound in a file</syntaxhighlight>

This is the <code>instruct</code>ion version, where the thing keeps the recording.
<syntaxhighlight lang="diego">begin_instruct(Record sound);
set_decision(linger);
find_thing()_first()_microphone()_bitrate(16)_tech(PCM)_samplerate(signed16, unsigned16)_rangefrom(8000, Hz)_rangeto(44100, Hz)_export(.wav)
? with_found()_label(recorder)_microphone()_label(mic);
: err_instruct[]_err(Sorry, no one has a microphone!);
exit_instruct[];
;
with_microphone[mic]_record()_durat({secs}, 30)_var(recording);
reset_decision();
end_instruct[];

// Record a monophonic 16-bit PCM sound into memory space:
exec_instruct(Record sound)_me();
with_thing[recorder]_microphone[mic]_var[recording]_var(PCMRecording); // The variable 'PCMRecording' is the sound in memory space

// Record a monophonic 16-bit PCM sound into a file or array:
exec_instruct(Record sound)_me();
with_thing[recorder]_microphone[mic]_var[recording]_file(foo.wav)_me(); // The file 'foo.wav' is the sound in a file</syntaxhighlight>

=={{header|FreeBASIC}}==
<syntaxhighlight lang="vbnet">#define PI 4 * Atn(1)

' Constants for the audio format
Dim Shared As Integer SAMPLE_RATE = 44100
Dim Shared As Integer BITS_PER_SAMPLE = 16
Dim Shared As Integer NUM_CHANNELS = 1

' Generates a sine wave
Sub generateSineWave(buffer() As Short, frequency As Double)
Dim As Double increment = 2.0 * PI * frequency / SAMPLE_RATE
Dim As Double x = 0.0
For i As Integer = 0 To Ubound(buffer)
buffer(i) = (Sin(x) * 32767.0)
x += increment
Next i
End Sub

' Write the header of the .wav file
Sub writeWaveHeader(file As Integer, numSamples As Integer)
' Write the RIFF header
Print #file, "RIFF";
Put #file, , numSamples * 2 + 36 ' File size
Print #file, "WAVE";
Dim As Integer SB = 16, FA = 1
' Write the fmt sub-block
Print #file, "fmt ";
Put #file, , SB ' Size of the fmt sub-block
Put #file, , FA ' Audio format (1 = PCM)
Put #file, , NUM_CHANNELS ' Number of channels
Put #file, , SAMPLE_RATE ' Sample rate
Put #file, , SAMPLE_RATE * NUM_CHANNELS * BITS_PER_SAMPLE / 8 ' Byte rate
Put #file, , NUM_CHANNELS * BITS_PER_SAMPLE / 8 ' Alineación de bloques
Put #file, , BITS_PER_SAMPLE ' Bits per sample
' Write the data sub-block
Print #file, "data";
Put #file, , numSamples * 2 ' Data size
End Sub

Dim As Integer file = Freefile
Open "output.wav" For Binary As #file

' Generates a 440 Hz sine wave for 5 seconds
Dim As Integer numSamples = SAMPLE_RATE * 5
Dim As Short buffer(numSamples - 1)
generateSineWave(buffer(), 440.0)

' Write the .wav file
writeWaveHeader(file, numSamples)
Put #file, , buffer()

Close #file</syntaxhighlight>


=={{header|Go}}==
=={{header|Go}}==
Line 280: Line 375:


The file name, sampling rate and duration can all be set by the user.
The file name, sampling rate and duration can all be set by the user.
<lang go>package main
<syntaxhighlight lang="go">package main


import (
import (
Line 340: Line 435:
check(err)
check(err)
fmt.Println("Play-back completed.")
fmt.Println("Play-back completed.")
}</lang>
}</syntaxhighlight>


=={{header|Diego}}==
=={{header|GUISS}}==
This <code>instruct</code>ion understands that the found <code>thing</code> has a microphone, so will have microphone knowledge. If the caller does not have microphone knowledge, the callee will train the caller on first request.
<lang diego>begin_funct({wav}, Record sound);
set_decision(linger);
find_thing()_first()_microphone()_bitrate(16)_tech(PCM)_samplerate(signed16, unsigned16)_rangefrom(8000, Hz)_rangeto(44100, Hz)_export(.wav)
? with_found()_label(recorder)_microphone()_label(mic);
: err_instruct[]_err(Sorry, no one has a microphone!);
exit_instruct[];
;
with_microphone[mic]_record()_durat({secs}, 30)_var(recording);
[Record sound]_ret([recording]);
reset_decision();
end_funct[];


Here we activate the Microsoft Windows '95 Sound Recorder:
// Record a monophonic 16-bit PCM sound into memory space:
exec_funct(Record sound)_var(PCMRecording)_me(); // The variable 'PCMRecording' is the sound in memory space


<syntaxhighlight lang="guiss">Start,Programs,Accessories,Sound Recorder,Button:Record</syntaxhighlight>
// Record a monophonic 16-bit PCM sound into a file or array:
exec_funct(Record sound)_file(foo.wav)_me(); // The file 'foo.wav' is the sound in a file</lang>


=={{header|GUISS}}==
=={{header|Java}}==
Java can record sound without external libraries.
<syntaxhighlight lang="java">
import java.io.IOException;
import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.TimeUnit;
import java.io.File;


import javax.sound.sampled.AudioFileFormat.*;
Here we activate the Microsoft Windows '95 Sound Recorder:


public final class SoundRecorder {
<lang guiss>Start,Programs,Accessories,Sound Recorder,Button:Record</lang>

public static void main(String[] args) {
SoundRecorder recorder = new SoundRecorder();
ScheduledExecutorService scheduler = Executors.newSingleThreadScheduledExecutor();
scheduler.schedule( () -> recorder.finish(), 10, TimeUnit.SECONDS);
scheduler.shutdown();

recorder.start();
}
private void start() {
try {
AudioFormat format = createAudioFormat();
DataLine.Info info = new DataLine.Info(TargetDataLine.class, format);
if ( ! AudioSystem.isLineSupported(info) ) {
System.out.println("Data line format is not supported");
Runtime.getRuntime().exit(0);
}
line = (TargetDataLine) AudioSystem.getLine(info);
line.open(format);
line.start();
System.out.println("Starting to capture and record audio");
AudioInputStream audioInputStream = new AudioInputStream(line);
AudioSystem.write(audioInputStream, audioFileType, wavFile);
} catch (LineUnavailableException | IOException exception) {
exception.printStackTrace(System.err);
}
}

private AudioFormat createAudioFormat() {
final float sampleRate = 16_000.0F;
final int sampleSizeInBits = 16;
final int channels = 1;
final boolean signed = true;
final boolean bigEndian = true;
// Monophonic 16-bit PCM audio format
return new AudioFormat(sampleRate, sampleSizeInBits, channels, signed, bigEndian);
}

private void finish() {
line.stop();
line.close();
System.out.println("Finished capturing and recording audio");
}
private TargetDataLine line;
private final File wavFile = new File("SoundRecorder.wav");
private final AudioFileFormat.Type audioFileType = AudioFileFormat.Type.WAVE;
}</syntaxhighlight>


=={{header|Julia}}==
=={{header|Julia}}==
<syntaxhighlight lang="julia">
<lang Julia>
using PortAudio, LibSndFile
using PortAudio, LibSndFile


Line 375: Line 519:
buf = read(stream, 441000)
buf = read(stream, 441000)
save("recorded10sec.wav", buf)
save("recorded10sec.wav", buf)
</syntaxhighlight>
</lang>


=={{header|Kotlin}}==
=={{header|Kotlin}}==
{{trans|Scala}}
{{trans|Scala}}
<lang scala>// version 1.1.3
<syntaxhighlight lang="scala">// version 1.1.3


import java.io.File
import java.io.File
Line 423: Line 567:
println(lue.message)
println(lue.message)
}
}
}</lang>
}</syntaxhighlight>


=={{header|Liberty BASIC}}==
=={{header|Liberty BASIC}}==
LB can easily send a MCI string to the OS, or extra routines eg SOX, so a minimal solution could be
LB can easily send a MCI string to the OS, or extra routines eg SOX, so a minimal solution could be
<syntaxhighlight lang="lb">
<lang lb>
run "sndrec32.exe"
run "sndrec32.exe"
</syntaxhighlight>
</lang>
A more direct way is..
A more direct way is..
<syntaxhighlight lang="lb">
<lang lb>
print "Starting 5 sec. recording..."
print "Starting 5 sec. recording..."
r$ =mciSendString$( "open new type waveaudio alias capture")
r$ =mciSendString$( "open new type waveaudio alias capture")
Line 466: Line 610:
end if
end if
end function
end function
</syntaxhighlight>
</lang>


=={{header|LiveCode}}==
=={{header|LiveCode}}==
This example sets some aspects of a sound recording individually and also shows use of the sound input dialog where a user can conveniently set them as well, either may be used.<lang LiveCode>command makeRecording
This example sets some aspects of a sound recording individually and also shows use of the sound input dialog where a user can conveniently set them as well, either may be used.<syntaxhighlight lang="livecode">command makeRecording
set the dontUseQT to false -- on windows use true
set the dontUseQT to false -- on windows use true
set the recordFormat to "wave" -- can be wav,aiff, au
set the recordFormat to "wave" -- can be wav,aiff, au
Line 481: Line 625:
stop recording
stop recording
end if
end if
end makeRecording</lang>
end makeRecording</syntaxhighlight>


=={{header|Mathematica}}/{{header|Wolfram Language}}==
=={{header|Mathematica}}/{{header|Wolfram Language}}==
<lang Mathematica>SystemDialogInput["RecordSound"]</lang>
<syntaxhighlight lang="mathematica">SystemDialogInput["RecordSound"]</syntaxhighlight>


=={{header|Nim}}==
=={{header|Nim}}==
Line 490: Line 634:
This code is for Linux systems and uses “arecord” and “aplay”. Previous code which used “/dev/dsp” no longer works on modern OS.
This code is for Linux systems and uses “arecord” and “aplay”. Previous code which used “/dev/dsp” no longer works on modern OS.
This code is a direct translation from Go version, but uses integers instead of floats for duration.
This code is a direct translation from Go version, but uses integers instead of floats for duration.
<lang nim>import osproc, strutils
<syntaxhighlight lang="nim">import osproc, strutils


var name = ""
var name = ""
Line 517: Line 661:
echo "'$1' created on disk and will now be played back..." % name
echo "'$1' created on disk and will now be played back..." % name
echo execProcess("aplay", args = [name], options = {poStdErrToStdOut, poUsePath})
echo execProcess("aplay", args = [name], options = {poStdErrToStdOut, poUsePath})
echo "Playback completed"</lang>
echo "Playback completed"</syntaxhighlight>


=={{header|OCaml}}==
=={{header|OCaml}}==
{{trans|C}}
{{trans|C}}


<lang ocaml>#load "unix.cma"
<syntaxhighlight lang="ocaml">#load "unix.cma"
let record bytes =
let record bytes =
Line 542: Line 686:
let bytes = 65536 in
let bytes = 65536 in
let p = record bytes in
let p = record bytes in
play p bytes</lang>
play p bytes</syntaxhighlight>


=={{header|Phix}}==
=={{header|Phix}}==
Line 548: Line 692:
{{trans|C}}
{{trans|C}}
{{trans|Go}}
{{trans|Go}}
<!--<lang Phix>(notonline)-->
<!--<syntaxhighlight lang="phix">(notonline)-->
<span style="color: #000080;font-style:italic;">--
<span style="color: #000080;font-style:italic;">--
-- demo\rosetta\Record_sound.exw
-- demo\rosetta\Record_sound.exw
Line 633: Line 777:
-- printf(1,"Play-back completed.\n")</span>
-- printf(1,"Play-back completed.\n")</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">if</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">if</span>
<!--</lang>-->
<!--</syntaxhighlight>-->


=={{header|PicoLisp}}==
=={{header|PicoLisp}}==


<lang PicoLisp>(in '(rec -q -c1 -tu16 - trim 0 2) # Record 2 seconds
<syntaxhighlight lang="picolisp">(in '(rec -q -c1 -tu16 - trim 0 2) # Record 2 seconds
(make
(make
(while (rd 2)
(while (rd 2)
(link @) ) ) )</lang>
(link @) ) ) )</syntaxhighlight>


Output:
Output:
Line 647: Line 791:
=={{header|Python}}==
=={{header|Python}}==


<lang python>import pyaudio
<syntaxhighlight lang="python">import pyaudio


chunk = 1024
chunk = 1024
Line 663: Line 807:


data = stream.read(chunk)
data = stream.read(chunk)
print [ord(i) for i in data]</lang>
print [ord(i) for i in data]</syntaxhighlight>


=={{header|Racket}}==
=={{header|Racket}}==
{{trans|C}}
{{trans|C}}
<lang racket>
<syntaxhighlight lang="racket">
#lang racket
#lang racket
(define (record n) (with-input-from-file "/dev/dsp" ( () (read-bytes n))))
(define (record n) (with-input-from-file "/dev/dsp" ( () (read-bytes n))))
(define (play bs) (display-to-file bs "/dev/dsp" #:exists 'append))
(define (play bs) (display-to-file bs "/dev/dsp" #:exists 'append))
(play (record 65536))
(play (record 65536))
</syntaxhighlight>
</lang>


=={{header|Raku}}==
=={{header|Raku}}==
(formerly Perl 6)
(formerly Perl 6)
Slightly modified from an example provided with the <code>Audio::PortAudio</code> module distribution.
Slightly modified from an example provided with the <code>Audio::PortAudio</code> module distribution.
<lang perl6>use Audio::PortAudio;
<syntaxhighlight lang="raku" line>use Audio::PortAudio;
use Audio::Sndfile;
use Audio::Sndfile;


Line 745: Line 889:
}
}


}</lang>
}</syntaxhighlight>


=={{header|Scala}}==
=={{header|Scala}}==
{{libheader|Scala}}
{{libheader|Scala}}
<lang Scala>import java.io.{File, IOException}
<syntaxhighlight lang="scala">import java.io.{File, IOException}
import javax.sound.sampled.{AudioFileFormat, AudioFormat, AudioInputStream}
import javax.sound.sampled.{AudioFileFormat, AudioFormat, AudioInputStream}
import javax.sound.sampled.{AudioSystem, DataLine, LineUnavailableException, TargetDataLine}
import javax.sound.sampled.{AudioSystem, DataLine, LineUnavailableException, TargetDataLine}
Line 799: Line 943:
case ioe: IOException => ioe.printStackTrace()
case ioe: IOException => ioe.printStackTrace()
}
}
}</lang>
}</syntaxhighlight>


=={{header|Tcl}}==
=={{header|Tcl}}==
{{libheader|Snack}}<lang tcl>package require sound
{{libheader|Snack}}<syntaxhighlight lang="tcl">package require sound


# Helper to do a responsive wait
# Helper to do a responsive wait
Line 820: Line 964:


# Destroy the recording object
# Destroy the recording object
$recording destroy</lang>
$recording destroy</syntaxhighlight>


=={{header|Wee Basic}}==
=={{header|Wee Basic}}==
<lang Wee Basic>print 1 "Recording..."
<syntaxhighlight lang="wee basic">print 1 "Recording..."
micrec
micrec
print 1 "Playing..."
print 1 "Playing..."
micpla
micpla
end</lang>
end</syntaxhighlight>


=={{header|Wren}}==
=={{header|Wren}}==
{{trans|Go}}
{{trans|Go}}
The ability to call external processes such as ''arecord'' is expected to be added to Wren-cli in the next release. In the meantime, we embed the following Wren script in a C host to complete this task.
The ability to call external processes such as ''arecord'' is expected to be added to Wren-cli in the next release. In the meantime, we embed the following Wren script in a C host to complete this task.
<lang ecmascript>/* record_sound.wren */
<syntaxhighlight lang="wren">/* Record_sound.wren */


class C {
class C {
Line 870: Line 1,014:
System.print("\n'%(name)' created on disk and will now be played back...")
System.print("\n'%(name)' created on disk and will now be played back...")
C.aplay(name)
C.aplay(name)
System.print("\nPlay-back completed.")</lang>
System.print("\nPlay-back completed.")</syntaxhighlight>
<br>
<br>
We now embed this in the following C program, compile and run it.
We now embed this in the following C program, compile and run it.
<lang c>#include <stdio.h>
<syntaxhighlight lang="c">#include <stdio.h>
#include <stdio_ext.h>
#include <stdio_ext.h>
#include <stdlib.h>
#include <stdlib.h>
Line 958: Line 1,102:
WrenVM* vm = wrenNewVM(&config);
WrenVM* vm = wrenNewVM(&config);
const char* module = "main";
const char* module = "main";
const char* fileName = "record_sound.wren";
const char* fileName = "Record_sound.wren";
char *script = readFile(fileName);
char *script = readFile(fileName);
WrenInterpretResult result = wrenInterpret(vm, module, script);
WrenInterpretResult result = wrenInterpret(vm, module, script);
Line 974: Line 1,118:
free(script);
free(script);
return 0;
return 0;
}</lang>
}</syntaxhighlight>

Latest revision as of 16:25, 3 April 2024

Task
Record sound
You are encouraged to solve this task according to the task description, using any language you may know.

Record a monophonic 16-bit PCM sound into either memory space, a file or array.

(This task neglects to specify the sample rate, and whether to use signed samples. The programs in this page might use signed 16-bit or unsigned 16-bit samples, at 8000 Hz, 44100 Hz, or any other sample rate. Therefore, these programs might not record sound in the same format.)

AutoHotkey

name := "sample"
waitsec := 5
Tooltip Recording %name%.wav
MCI_SendString("close all wait")
MCI_SendString("open new type waveaudio alias " . name)
MCI_SendString("set " . name . " time format ms wait")
;MCI_SendString("set " . name . " bitspersample 16 wait")
;MCI_SendString("set " . name . " channels 1 wait")
;MCI_SendString("set " . name . " samplespersec 16000 wait")
;MCI_SendString("set " . name . " alignment 1 wait")
;MCI_SendString("set " . name . " bytespersec 8000 wait")
MCI_SendString("record " . name)
Sleep waitsec*1000
MCI_SendString("stop " . name . " wait")
MCI_SendString("save " . name . " """ . name . ".wav""")
Tooltip Finished ... Playing
MCI_SendString("delete " . name)
MCI_SendString("close " . name . " wait")
MCI_SendString("open """ . name . ".wav"" type waveaudio alias " . name)
MCI_SendString("play " . name . " wait")
MCI_SendString("close " . name . " wait")
Tooltip
Return

MCI_SendString(p_lpszCommand,ByRef r_lpszReturnString="",p_hwndCallback=0) {
	VarSetCapacity(r_lpszReturnString,512,0)
	Return DllCall("winmm.dll\mciSendString" . (A_IsUnicode ? "W":"A")
		,"Str",p_lpszCommand						;-- lpszCommand
		,"Str",r_lpszReturnString					;-- lpszReturnString
		,"UInt",512									;-- cchReturn
		,A_PtrSize ? "Ptr":"UInt",p_hwndCallback	;-- hwndCallback
		,"Cdecl Int")								;-- Return type
}
; For more intuitive functions, see the MCI library by jballi.
; doc: http://www.autohotkey.net/~jballi/MCI/v1.1/MCI.html
; download: http://www.autohotkey.net/~jballi/MCI/v1.1/MCI.ahk

BBC BASIC

      wavfile$ = @dir$ + "capture.wav"
      bitspersample% = 16
      channels% = 2
      samplespersec% = 44100
 
      alignment% = bitspersample% * channels% / 8
      bytespersec% = alignment% * samplespersec%
 
      params$ = " bitspersample " + STR$(bitspersample%) + \
      \         " channels " + STR$(channels%) + \
      \         " alignment " + STR$(alignment%) + \
      \         " samplespersec " + STR$(samplespersec%) + \
      \         " bytespersec " + STR$(bytespersec%)
 
      SYS "mciSendString", "close all", 0, 0, 0
      SYS "mciSendString", "open new type waveaudio alias capture", 0, 0, 0
      SYS "mciSendString", "set capture" + params$, 0, 0, 0 TO res%
      IF res% ERROR 100, "Couldn't set capture parameters: " + STR$(res% AND &FFFF)
 
      PRINT "Press SPACE to start recording..."
      REPEAT UNTIL INKEY(1) = 32
 
      SYS "mciSendString", "record capture", 0, 0, 0 TO res%
      IF res% ERROR 100, "Couldn't start audio capture: " + STR$(res% AND &FFFF)
 
      PRINT "Recording, press SPACE to stop..."
      REPEAT UNTIL INKEY(1) = 32
 
      SYS "mciSendString", "stop capture", 0, 0, 0
      SYS "mciSendString", "save capture " + wavfile$, 0, 0, 0 TO res%
      IF res% ERROR 100, "Couldn't save to WAV file: " + STR$(res% AND &FFFF)
 
      SYS "mciSendString", "delete capture", 0, 0, 0
      SYS "mciSendString", "close capture", 0, 0, 0
 
      PRINT "Captured audio is stored in " wavfile$

C

Read/write raw device /dev/dsp. On Linux you need access to said device, meaning probably you should be in audio user group.

#include <stdlib.h>
#include <unistd.h>
#include <sys/types.h>
#include <fcntl.h>

void * record(size_t bytes)
{
	int fd;
	if (-1 == (fd = open("/dev/dsp", O_RDONLY))) return 0;
	void *a = malloc(bytes);
	read(fd, a, bytes);
	close(fd);
	return a;
}

int play(void *buf, size_t len)
{
	int fd;
	if (-1 == (fd = open("/dev/dsp", O_WRONLY))) return 0;
	write(fd, buf, len);
	close(fd);
	return 1;
}

int main()
{
	void *p = record(65536);
	play(p, 65536);
	return 0;
}

C++

Uses Windows MCI

#include <iostream>
#include <string>
#include <windows.h>
#include <mmsystem.h>

#pragma comment ( lib, "winmm.lib" )
using namespace std;

class recorder
{
public:
    void start()
    {
	paused = rec = false; action = "IDLE";
	while( true )
	{
	    cout << endl << "==" << action << "==" << endl << endl;
	    cout << "1) Record" << endl << "2) Play" << endl << "3) Pause" << endl << "4) Stop" << endl << "5) Quit" << endl;
	    char c; cin >> c;
	    if( c > '0' && c < '6' )
	    {
		switch( c )
		{
		    case '1': record(); break;
		    case '2': play();   break;
		    case '3': pause();  break;
		    case '4': stop();   break;
		    case '5': stop();   return;
		}
	    }
	}
    }
private:
    void record()
    {
	if( mciExecute( "open new type waveaudio alias my_sound") )
	{ 
	    mciExecute( "record my_sound" ); 
	    action = "RECORDING"; rec = true; 
	}
    }
    void play()
    {
	if( paused )
	    mciExecute( "play my_sound" );
	else
	    if( mciExecute( "open tmp.wav alias my_sound" ) )
		mciExecute( "play my_sound" );

	action = "PLAYING";
	paused = false;
    }
    void pause()
    {
	if( rec ) return;
	mciExecute( "pause my_sound" );
	paused = true; action = "PAUSED";
    }
    void stop()
    {
	if( rec )
	{
	    mciExecute( "stop my_sound" );
	    mciExecute( "save my_sound tmp.wav" );
	    mciExecute( "close my_sound" );
	    action = "IDLE"; rec = false;
	}
	else
	{
	    mciExecute( "stop my_sound" );
	    mciExecute( "close my_sound" );
	    action = "IDLE";
	}
    }
    bool mciExecute( string cmd )
    {
	if( mciSendString( cmd.c_str(), NULL, 0, NULL ) )
	{
	    cout << "Can't do this: " << cmd << endl;
	    return false;
	}
	return true;
    }

    bool paused, rec;
    string action;
};

int main( int argc, char* argv[] )
{
    recorder r; r.start();
    return 0;
}

ChucK

// chuck this with other shreds to record to file
// example> chuck foo.ck bar.ck rec 

// arguments: rec:<filename>

// get name
me.arg(0) => string filename;
if( filename.length() == 0 ) "foo.wav" => filename;

// pull samples from the dac
dac => Gain g => WvOut w => blackhole;
// this is the output file name
filename => w.wavFilename;
<<<"writing to file:", "'" + w.filename() + "'">>>;
// any gain you want for the output
.5 => g.gain;

// temporary workaround to automatically close file on remove-shred
null @=> w;

// infinite time loop...
// ctrl-c will stop it, or modify to desired duration
while( true ) 1::second => now;

Common Lisp

Translation of: C
(defun record (n)
  (with-open-file (in "/dev/dsp" :element-type '(unsigned-byte 8))
    (loop repeat n collect (read-byte in))
    )
  )
(defun play (byte-list)
  (with-open-file (out "/dev/dsp" :direction :output :element-type '(unsigned-byte 8) :if-exists :append)
    (mapcar (lambda (b) (write-byte b out)) byte-list)
    )
  )
(play (record 65536))

Diego

This function returns a {wav} variable recorded from a thing in the mist. It understands that the found thing has a microphone, so will have microphone knowledge. If the caller does not have microphone knowledge, the callee will train the caller on first request.

begin_funct({wav}, Record sound);
    set_decision(linger);
    find_thing()_first()_microphone()_bitrate(16)_tech(PCM)_samplerate(signed16, unsigned16)_rangefrom(8000, Hz)_rangeto(44100, Hz)_export(.wav)
        ? with_found()_microphone()_label(mic);
        : err_funct[]_err(Sorry, no one has a microphone!);
          exit_funct[];
    ;
    with_microphone[mic]_record()_durat({secs}, 30)_var(recording);
    [Record sound]_ret([recording]);
    reset_decision();
end_funct[];

// Record a monophonic 16-bit PCM sound into memory space:
exec_funct(Record sound)_var(PCMRecording)_me();         // The variable 'PCMRecording' is the sound in memory space

// Record a monophonic 16-bit PCM sound into a file or array:
exec_funct(Record sound)_file(foo.wav)_me();         // The file 'foo.wav' is the sound in a file

This is the instruction version, where the thing keeps the recording.

begin_instruct(Record sound);
    set_decision(linger);
    find_thing()_first()_microphone()_bitrate(16)_tech(PCM)_samplerate(signed16, unsigned16)_rangefrom(8000, Hz)_rangeto(44100, Hz)_export(.wav)
        ? with_found()_label(recorder)_microphone()_label(mic);
        : err_instruct[]_err(Sorry, no one has a microphone!);
          exit_instruct[];
    ;
    with_microphone[mic]_record()_durat({secs}, 30)_var(recording);
    reset_decision();
end_instruct[];

// Record a monophonic 16-bit PCM sound into memory space:
exec_instruct(Record sound)_me();
with_thing[recorder]_microphone[mic]_var[recording]_var(PCMRecording);  // The variable 'PCMRecording' is the sound in memory space

// Record a monophonic 16-bit PCM sound into a file or array:
exec_instruct(Record sound)_me();
with_thing[recorder]_microphone[mic]_var[recording]_file(foo.wav)_me();         // The file 'foo.wav' is the sound in a file

FreeBASIC

#define PI 4 * Atn(1)

' Constants for the audio format
Dim Shared As Integer SAMPLE_RATE = 44100
Dim Shared As Integer BITS_PER_SAMPLE = 16
Dim Shared As Integer NUM_CHANNELS = 1

' Generates a sine wave
Sub generateSineWave(buffer() As Short, frequency As Double)
    Dim As Double increment = 2.0 * PI * frequency / SAMPLE_RATE
    Dim As Double x = 0.0
    For i As Integer = 0 To Ubound(buffer)
        buffer(i) = (Sin(x) * 32767.0)
        x += increment
    Next i
End Sub

' Write the header of the .wav file
Sub writeWaveHeader(file As Integer, numSamples As Integer)
    ' Write the RIFF header
    Print #file, "RIFF";
    Put #file, , numSamples * 2 + 36  ' File size
    Print #file, "WAVE";
    
    Dim As Integer SB = 16, FA = 1
    ' Write the fmt sub-block
    Print #file, "fmt ";
    Put #file, , SB                 ' Size of the fmt sub-block
    Put #file, , FA                 ' Audio format (1 = PCM)
    Put #file, , NUM_CHANNELS       ' Number of channels
    Put #file, , SAMPLE_RATE        ' Sample rate
    Put #file, , SAMPLE_RATE * NUM_CHANNELS * BITS_PER_SAMPLE / 8   ' Byte rate
    Put #file, , NUM_CHANNELS * BITS_PER_SAMPLE / 8   ' Alineación de bloques
    Put #file, , BITS_PER_SAMPLE    ' Bits per sample
    
    ' Write the data sub-block
    Print #file, "data";
    Put #file, , numSamples * 2     ' Data size
End Sub

Dim As Integer file = Freefile
Open "output.wav" For Binary As #file

' Generates a 440 Hz sine wave for 5 seconds
Dim As Integer numSamples = SAMPLE_RATE * 5
Dim As Short buffer(numSamples - 1)
generateSineWave(buffer(), 440.0)

' Write the .wav file
writeWaveHeader(file, numSamples)
Put #file, , buffer()

Close #file

Go

Works with: Ubuntu 16.04


As Go does not have any audio support in its standard library, this invokes the 'arecord' command-line utility to record sound from the internal microphone (assuming there's no other audio input device present) and saves it to a monophonic, signed 16-bit .wav file. It then plays it back using the 'aplay' utility.

The file name, sampling rate and duration can all be set by the user.

package main

import (
    "bufio"
    "fmt"
    "log"
    "os"
    "os/exec"
    "strconv"
)

func check(err error) {
    if err != nil {
        log.Fatal(err)
    }
}

func main() {
    scanner := bufio.NewScanner(os.Stdin)
    name := ""
    for name == "" {
        fmt.Print("Enter output file name (without extension) : ")
        scanner.Scan()
        name = scanner.Text()
        check(scanner.Err())
    }
    name += ".wav"

    rate := 0
    for rate < 2000 || rate > 192000 {
        fmt.Print("Enter sampling rate in Hz (2000 to 192000) : ")
        scanner.Scan()
        input := scanner.Text()
        check(scanner.Err())
        rate, _ = strconv.Atoi(input)
    }
    rateS := strconv.Itoa(rate)

    dur := 0.0
    for dur < 5 || dur > 30 {
        fmt.Print("Enter duration in seconds (5 to 30)        : ")
        scanner.Scan()
        input := scanner.Text()
        check(scanner.Err())
        dur, _ = strconv.ParseFloat(input, 64)
    }
    durS := strconv.FormatFloat(dur, 'f', -1, 64)

    fmt.Println("OK, start speaking now...")
    // Default arguments: -c 1, -t wav. Note only signed 16 bit format supported.
    args := []string{"-r", rateS, "-f", "S16_LE", "-d", durS, name}
    cmd := exec.Command("arecord", args...)
    err := cmd.Run()
    check(err)

    fmt.Printf("'%s' created on disk and will now be played back...\n", name)
    cmd = exec.Command("aplay", name)
    err = cmd.Run()
    check(err)
    fmt.Println("Play-back completed.")
}

GUISS

Here we activate the Microsoft Windows '95 Sound Recorder:

Start,Programs,Accessories,Sound Recorder,Button:Record

Java

Java can record sound without external libraries.

import java.io.IOException;
import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.TimeUnit;
import java.io.File;

import javax.sound.sampled.AudioFileFormat.*;

public final class SoundRecorder {

    public static void main(String[] args) {
    	SoundRecorder recorder = new SoundRecorder();
        
        ScheduledExecutorService scheduler = Executors.newSingleThreadScheduledExecutor();
        scheduler.schedule( () -> recorder.finish(), 10, TimeUnit.SECONDS);
        scheduler.shutdown(); 

        recorder.start();
    }   
 
    private void start() {
        try {
            AudioFormat format = createAudioFormat();
            DataLine.Info info = new DataLine.Info(TargetDataLine.class, format);
 
            if ( ! AudioSystem.isLineSupported(info) ) {
                System.out.println("Data line format is not supported");
                Runtime.getRuntime().exit(0);
            }            
            
            line = (TargetDataLine) AudioSystem.getLine(info);
            line.open(format);
            line.start(); 
            
            System.out.println("Starting to capture and record audio");
            AudioInputStream audioInputStream = new AudioInputStream(line); 
            AudioSystem.write(audioInputStream, audioFileType, wavFile);             
            
        } catch (LineUnavailableException | IOException exception) {
            exception.printStackTrace(System.err);
        }
    }

    private AudioFormat createAudioFormat() {
        final float sampleRate = 16_000.0F;
        final int sampleSizeInBits = 16;
        final int channels = 1;
        final boolean signed = true;
        final boolean bigEndian = true;
        // Monophonic 16-bit PCM audio format
        return new AudioFormat(sampleRate, sampleSizeInBits, channels, signed, bigEndian);
    }

    private void finish() {
        line.stop();
        line.close(); 
        System.out.println("Finished capturing and recording audio");
    }
    
    private TargetDataLine line;
    
    private final File wavFile = new File("SoundRecorder.wav"); 
    private final AudioFileFormat.Type audioFileType = AudioFileFormat.Type.WAVE;    
    
}

Julia

using PortAudio, LibSndFile

stream = PortAudioStream("Microphone (USB Microphone)", 1, 0) # 44100 samples/sec
buf = read(stream, 441000)
save("recorded10sec.wav", buf)

Kotlin

Translation of: Scala
// version 1.1.3

import java.io.File
import javax.sound.sampled.*

const val RECORD_TIME = 20000L // twenty seconds say

fun main(args: Array<String>) {
    val wavFile = File("RecordAudio.wav")
    val fileType = AudioFileFormat.Type.WAVE
    val format = AudioFormat(16000.0f, 16, 2, true, true)
    val info = DataLine.Info(TargetDataLine::class.java, format)
    val line = AudioSystem.getLine(info) as TargetDataLine

    // Creates a new thread that waits for 'RECORD_TIME' before stopping
    Thread(object: Runnable {
        override fun run() {
            try {
                Thread.sleep(RECORD_TIME)
            }
            catch (ie: InterruptedException) {
                println(ie.message)
            }
            finally {
                line.stop()
                line.close()
            }
            println("Finished")
         }
    }).start()

    // Captures the sound and saves it in a WAV file             
    try {
        if (AudioSystem.isLineSupported(info)) {
            line.open(format)
            line.start()
            println("Recording started")
            AudioSystem.write(AudioInputStream(line), fileType, wavFile)
        }
        else println("Line not supported")
    }
    catch (lue: LineUnavailableException) {
        println(lue.message)
    }
}

Liberty BASIC

LB can easily send a MCI string to the OS, or extra routines eg SOX, so a minimal solution could be

run "sndrec32.exe"

A more direct way is..

    print "Starting 5 sec. recording..."
    r$ =mciSendString$( "open new type waveaudio alias capture")
    r$ =mciSendString$( "set capture time format ms bitspersample 16")
    r$ =mciSendString$( "set capture channels 1 samplespersec 8000")
    r$ =mciSendString$( "set capture alignment 1 bytespersec 8000")
    r$ =mciSendString$( "record capture")
    timer 5000, [on]
    wait
  [on]
    timer 0
    print "     .... now stopping the recording."
    r$ =mciSendString$( "stop capture")
    r$ =mciSendString$( "save capture " +chr$( 34) +"sample.wav" +chr$( 34))
    r$ =mciSendString$( "close capture")    
    print "Done recording."
    r$=mciSendString$( "open " +q$ +"sample.wav" +q$ +" type waveaudio alias sfx")
    r$=mciSendString$( "play sfx wait")
    r$=mciSendString$( "close sfx")
    print "Done playing back."
    end

function mciSendString$( s$)
    print s$
    buffer$ =space$( 1024) +chr$( 0)
    calldll #winmm, "mciSendStringA", s$ as ptr, buffer$ as ptr, 1028 as long, 0 as long, r as long
    buffer$ =left$( buffer$, instr( buffer$, chr$( 0)) -1)
    if r >0 then
        mciSendString$ ="error"
        print "returned "; mciSendString$
    else
        mciSendString$ =""'buffer$
        print "OK"
    end if
end function

LiveCode

This example sets some aspects of a sound recording individually and also shows use of the sound input dialog where a user can conveniently set them as well, either may be used.

command makeRecording
    set the dontUseQT to false -- on windows use true
    set the recordFormat to "wave" -- can be wav,aiff, au
    set the recordRate to 44.1 -- sample at 44100 Hz
    set the recordSampleSize to 16  --default is 8 bit
    ask file "Save recording as" 
    if it is not empty then
        answer record --show sound input dialog with presets above
        record sound file it  -- actual record command
        wait 10 seconds
        stop recording 
    end if
end makeRecording

Mathematica/Wolfram Language

SystemDialogInput["RecordSound"]

Nim

Translation of: Go

This code is for Linux systems and uses “arecord” and “aplay”. Previous code which used “/dev/dsp” no longer works on modern OS. This code is a direct translation from Go version, but uses integers instead of floats for duration.

import osproc, strutils

var name = ""
while name.len == 0:
  stdout.write "Enter output file name (without extension): "
  name = stdin.readLine().strip()
name.add ".wav"

var rate = 0
while rate notin 2000..19_200:
  stdout.write "Enter sampling rate in Hz (2000 to 192000): "
  try: rate = parseInt(stdin.readLine().strip())
  except ValueError: discard

var duration = 0
while duration notin 5..30:
  stdout.write "Enter duration in seconds (5 to 30): "
  try: duration = parseInt(stdin.readLine().strip())
  except ValueError: discard

echo "OK, start speaking now..."
# Default arguments: -c 1, -t wav. Note that only signed 16 bit format is supported.
let args = ["-r", $rate, "-f", "S16_LE", "-d", $duration, name]
echo execProcess("arecord", args = args, options = {poStdErrToStdOut, poUsePath})

echo "'$1' created on disk and will now be played back..." % name
echo execProcess("aplay", args = [name], options = {poStdErrToStdOut, poUsePath})
echo "Playback completed"

OCaml

Translation of: C
#load "unix.cma"
 
let record bytes =
  let buf = String.make bytes '\000' in
  let ic = open_in "/dev/dsp" in
  let chunk = 4096 in
  for i = 0 to pred (bytes / chunk) do
    ignore (input ic buf (i * chunk) chunk)
  done;
  close_in ic;
  (buf)
 
let play buf len =
  let oc = open_out "/dev/dsp" in
  output_string oc buf;
  close_out oc
 
let () =
  let bytes = 65536 in
  let p = record bytes in
  play p bytes

Phix

Translation of: BBC_BASIC
Translation of: C
Translation of: Go
--
-- demo\rosetta\Record_sound.exw
-- =============================
--
without js -- (file i/o)
constant wavfile = "capture.wav",
         bitspersample = 16,
         channels = 2,
         samplespersec = 44100,
         alignment = bitspersample * channels / 8,
         bytespersec = alignment * samplespersec,
         params = sprintf(" bitspersample %d channels %d alignment %d samplespersec %d bytespersec %d",
                           {bitspersample,   channels,   alignment,   samplespersec,   bytespersec}),
         error_size = 2048
atom winmm = NULL, xmciSendString, pError

procedure mciSendString(string msg)
    if winmm=NULL then
         winmm = open_dll("winmm.dll")
         xmciSendString = define_c_func(winmm,"mciSendStringA",
            {C_PTR,     --  LPCTSTR lpszCommand
             C_PTR,     --  LPTSTR lpszReturnString
             C_INT,     --  UINT cchReturn
             C_PTR},    --  HANDLE hwndCallback
            C_INT)      -- MCIERROR
         pError = allocate(error_size)
    end if
    atom res = c_func(xmciSendString,{msg,pError,error_size,NULL})
    if res!=0 then crash("error %0x: %s",{res,peek_string(pError)}) end if
end procedure

include get.e   -- get_bytes()

function record(integer bytes)
    integer fn = open("/dev/dsp","rb")
    if fn=-1 then return "" end if
    string res = get_bytes(fn,bytes)
    close(fn)
    return res
end function
 
procedure play(string buf)
    if length(buf) then
        integer fn = open("/dev/dsp","wb")
        if fn!=-1 then
            puts(fn,buf)
            close(fn)
        end if
    end if
end procedure

if platform()=WINDOWS then
    mciSendString("close all")
    mciSendString("open new type waveaudio alias capture")
    mciSendString("set capture" & params)

    puts(1,"Press SPACE to start recording...")
    while wait_key()!=' ' do end while
 
    mciSendString("record capture")
    puts(1,"Recording, press SPACE to stop...")
    while wait_key()!=' ' do end while
 
    mciSendString("stop capture")
    mciSendString("save capture " & wavfile)
    mciSendString("delete capture")
    mciSendString("close capture")
 
    puts(1,"Captured audio is stored in "&wavfile)
elsif platform()=LINUX then
    -- warning: untested
    play(record(65536))
--  -- alternative, from Go (ditto)
--  string name = "test.wav",
--         rate = "2000", -- (2000..192000 Hz)
--         durn = "5" -- (5 to 30 seconds)
--  printf(1,"OK, start speaking now...\n")
--  -- Default arguments: -c 1, -t wav. Note only signed 16 bit format supported.
--  string cmd = sprintf("arecord -r %s -f S16_LE -d %s %s", {rate,durn,name})
--  {} = system_exec(cmd)
--  printf(1,"'%s' created on disk and will now be played back...\n", {name})
--  {} = system_exec("aplay "&name)
--  printf(1,"Play-back completed.\n")
end if

PicoLisp

(in '(rec -q -c1 -tu16 - trim 0 2)  # Record 2 seconds
   (make
      (while (rd 2)
         (link @) ) ) )

Output:

-> (16767 19071 17279 ... 5503 9343 14719)  # 96000 numbers

Python

import pyaudio

chunk = 1024
FORMAT = pyaudio.paInt16
CHANNELS = 1
RATE = 44100

p = pyaudio.PyAudio()

stream = p.open(format = FORMAT,
                channels = CHANNELS,
                rate = RATE,
                input = True,
                frames_per_buffer = chunk)

data = stream.read(chunk)
print [ord(i) for i in data]

Racket

Translation of: C
#lang racket
(define (record n) (with-input-from-file "/dev/dsp" ( () (read-bytes n))))
(define (play bs)  (display-to-file bs "/dev/dsp" #:exists 'append))
(play (record 65536))

Raku

(formerly Perl 6) Slightly modified from an example provided with the Audio::PortAudio module distribution.

use Audio::PortAudio;
use Audio::Sndfile;

sub MAIN(Str $filename, Str :$source, Int :$buffer = 256) {
    my $pa = Audio::PortAudio.new;
    my $format = Audio::Sndfile::Info::Format::WAV +| Audio::Sndfile::Info::Subformat::PCM_16;
    my $out-file = Audio::Sndfile.new(:$filename, channels => 1, samplerate => 44100, :$format, :w);
    my $st;
    
    if $source.defined {
        my $index = 0;
        for $pa.devices -> $device {
            if $device.name eq $source {
                else {
                    my $la = $device.default-high-input-latency;
                    my $si = Audio::PortAudio::StreamParameters.new(device => $index,
                                                                    channel-count => 1,
                                                                    sample-format => Audio::PortAudio::StreamFormat::Float32,
                                                                    suggested-latency => ($la || 0.05e0 ));
                    $st = $pa.open-stream($si, Audio::PortAudio::StreamParameters, 44100, $buffer );
                    last;
                }

            }
            $index++;
        }
        die "Couldn't find a device for '$source'" if !$st.defined;
    }
    else {
        $st = $pa.open-default-stream(2,0, Audio::PortAudio::StreamFormat::Float32, 44100, $buffer);
    }
    $st.start;
    my $p = Promise.new;
    signal(SIGINT).act({
        say "stopping recording";
        $p.keep: "stopped";
        $out-file.close;
        $st.close;
        exit;
    });
    my Channel $write-channel = Channel.new;
    my $write-promise = start {
        react {
            whenever $write-channel -> $item {
                if $p.status ~~ Planned {
                    $out-file.write-float($item[0], $item[1]);
                    $out-file.sync;
                }
                else {
                    done;
                }
            }
        }
    };

    loop {
        if $p.status ~~ Planned {
            my $f = $buffer || $st.read-available;
            if $f > 0 {
                my $buff = $st.read($f,2, num32);
                $write-channel.send([$buff, $f]);
            }
        }
        else {
            last;
        }
    }

}

Scala

Library: Scala
import java.io.{File, IOException}
import javax.sound.sampled.{AudioFileFormat, AudioFormat, AudioInputStream}
import javax.sound.sampled.{AudioSystem, DataLine, LineUnavailableException, TargetDataLine}

object SoundRecorder extends App {
  // record duration, in milliseconds
  final val RECORD_TIME = 60000 // 1 minute

  // path and format of the wav file
  val (wavFile, fileType) = (new File("RecordAudio.wav"), AudioFileFormat.Type.WAVE)
  val format = new AudioFormat(/*sampleRate =*/ 16000f,
    /*sampleSizeInBits =*/ 16,
    /*channels =*/ 2,
    /*signed =*/ true,
    /*bigEndian =*/ true)

  val info = new DataLine.Info(classOf[TargetDataLine], format)
  val line: TargetDataLine = AudioSystem.getLine(info).asInstanceOf[TargetDataLine]

  // Entry to run the program

  // Creates a new thread that waits for a specified of time before stopping
  new Thread(new Runnable() {
    def run() {
      try {
        Thread.sleep(RECORD_TIME)
      } catch {
        case ex: InterruptedException => ex.printStackTrace()
      }
      finally {
        line.stop()
        line.close()
      }
      println("Finished")
    }
  }).start()

  //Captures the sound and record into a WAV file
  try {
    // checks if system supports the data line
    if (AudioSystem.isLineSupported(info)) {
      line.open(format)
      line.start() // start capturing
      println("Recording started")
      AudioSystem.write(new AudioInputStream(line), fileType, wavFile)
    } else println("Line not supported")
  } catch {
    case ex: LineUnavailableException => ex.printStackTrace()
    case ioe: IOException => ioe.printStackTrace()
  }
}

Tcl

Library: Snack
package require sound

# Helper to do a responsive wait
proc delay t {after $t {set ::doneDelay ok}; vwait ::doneDelay}

# Make an in-memory recording object
set recording [snack::sound -encoding "Lin16" -rate 44100 -channels 1]

# Set it doing the recording, wait for a second, and stop
$recording record -append true
delay 1000
$recording stop

# Convert the internal buffer to viewable numbers, and print them out
binary scan [$recording data -byteorder littleEndian] s* words
puts [join $words ", "]

# Destroy the recording object
$recording destroy

Wee Basic

print 1 "Recording..."
micrec
print 1 "Playing..."
micpla
end

Wren

Translation of: Go

The ability to call external processes such as arecord is expected to be added to Wren-cli in the next release. In the meantime, we embed the following Wren script in a C host to complete this task.

/* Record_sound.wren */

class C {
    foreign static getInput(maxSize)

    foreign static arecord(args)

    foreign static aplay(name)
}

var name = ""
while (name == "") {
    System.write("Enter output file name (without extension) : ")
    name = C.getInput(80)
}
name = name + ".wav"

var rate = 0
while (!rate || !rate.isInteger || rate < 2000 || rate > 192000) {
    System.write("Enter sampling rate in Hz (2000 to 192000) : ")
    rate = Num.fromString(C.getInput(6))
}
var rateS = rate.toString

var dur = 0
while (!dur || dur < 5 || dur > 30) {
    System.write("Enter duration in seconds (5 to 30)        : ")
    dur = Num.fromString(C.getInput(5))
}
var durS = dur.toString

System.print("\nOK, start speaking now...")
// Default arguments: -c 1, -t wav. Note only signed 16 bit format supported.
var args = ["-r", rateS, "-f", "S16_LE", "-d", durS, name]
C.arecord(args.join(" "))

System.print("\n'%(name)' created on disk and will now be played back...")
C.aplay(name)
System.print("\nPlay-back completed.")


We now embed this in the following C program, compile and run it.

#include <stdio.h>
#include <stdio_ext.h>
#include <stdlib.h>
#include <string.h>
#include "wren.h"

void C_getInput(WrenVM* vm) {
    int maxSize = (int)wrenGetSlotDouble(vm, 1) + 2;
    char input[maxSize];
    fgets(input, maxSize, stdin);
    __fpurge(stdin);
    input[strcspn(input, "\n")] = 0;
    wrenSetSlotString(vm, 0, (const char*)input);
}

void C_arecord(WrenVM* vm) {
    const char *args = wrenGetSlotString(vm, 1);
    char command[strlen(args) + 8];
    strcpy(command, "arecord ");
    strcat(command, args);
    system(command);
}

void C_aplay(WrenVM* vm) {
    const char *name = wrenGetSlotString(vm, 1);
    char command[strlen(name) + 6];
    strcpy(command, "aplay ");
    strcat(command, name);
    system(command);
}

WrenForeignMethodFn bindForeignMethod(
    WrenVM* vm,
    const char* module,
    const char* className,
    bool isStatic,
    const char* signature) {
    if (strcmp(module, "main") == 0) {
        if (strcmp(className, "C") == 0) {
            if (isStatic && strcmp(signature, "getInput(_)") == 0) return C_getInput;
            if (isStatic && strcmp(signature, "arecord(_)") == 0)  return C_arecord;
            if (isStatic && strcmp(signature, "aplay(_)") == 0)    return C_aplay;
        }
    }
    return NULL;
}

static void writeFn(WrenVM* vm, const char* text) {
    printf("%s", text);
}

void errorFn(WrenVM* vm, WrenErrorType errorType, const char* module, const int line, const char* msg) {
    switch (errorType) {
        case WREN_ERROR_COMPILE:
            printf("[%s line %d] [Error] %s\n", module, line, msg);
            break;
        case WREN_ERROR_STACK_TRACE:
            printf("[%s line %d] in %s\n", module, line, msg);
            break;
        case WREN_ERROR_RUNTIME:
            printf("[Runtime Error] %s\n", msg);
            break;
    }
}

char *readFile(const char *fileName) {
    FILE *f = fopen(fileName, "r");
    fseek(f, 0, SEEK_END);
    long fsize = ftell(f);
    rewind(f);
    char *script = malloc(fsize + 1);
    fread(script, 1, fsize, f);
    fclose(f);
    script[fsize] = 0;
    return script;
}

int main(int argc, char **argv) {
    WrenConfiguration config;
    wrenInitConfiguration(&config);
    config.writeFn = &writeFn;
    config.errorFn = &errorFn;
    config.bindForeignMethodFn = &bindForeignMethod;
    WrenVM* vm = wrenNewVM(&config);
    const char* module = "main";
    const char* fileName = "Record_sound.wren";
    char *script = readFile(fileName);
    WrenInterpretResult result = wrenInterpret(vm, module, script);
    switch (result) {
        case WREN_RESULT_COMPILE_ERROR:
            printf("Compile Error!\n");
            break;
        case WREN_RESULT_RUNTIME_ERROR:
            printf("Runtime Error!\n");
            break;
        case WREN_RESULT_SUCCESS:
            break;
    }
    wrenFreeVM(vm);
    free(script);
    return 0;
}