Skip to content

Instantly share code, notes, and snippets.

@aklaswad
Created October 16, 2011 16:19
Show Gist options
  • Select an option

  • Save aklaswad/1291096 to your computer and use it in GitHub Desktop.

Select an option

Save aklaswad/1291096 to your computer and use it in GitHub Desktop.
#!/usr/bin/perl
use strict;
use warnings;
BEGIN {
unshift @INC, '../lib';
}
use Sound::NeSynth;
my $kick = {
osc => {
freq => 55,
waveform => 'sin',
mod => { speed => 0.02, depth => 0.2, waveform => 'noise', curve => 1.4 }
},
amp => { sec => 0.28, waveform => 'env', curve => 4.5 }
};
my $snr1 = {
osc => {
freq => 1400,
waveform => 'tri',
mod => { speed => 1.12, depth => 1.0, waveform => 'noise' },
},
amp => { sec => 0.2, waveform => 'env', curve => 8.2 }
};
my $perc = {
osc => {
freq => 660,
waveform => 'pulse',
mod => { speed => 0.2, depth => 0.07, waveform => 'saw' },
},
amp => { sec => 0.26, waveform => 'env', curve => 3.2 }
};
my $c_hat = {
osc => {
freq => 9000,
waveform => 'noise',
mod => { speed => 1.03, depth => 4.0, waveform => 'noise' }
},
amp => { sec => 0.09, waveform => 'env', curve => 8.0 }
};
my %patterns = (
kick => [ 0,0,1,1,0,0,0,0, 1,0,0,0,0,1,0,0, 0,0,1,0,0,1,0,0, 0,0,1,1,0,0,0,0, 0,0,1,0,0,0,0,1, 0,0,1,1,0,0,0,0, 0,0,1,0,0,0,0,0, 1,0,0,1,0,0,1,0 ],
snr1 => [ 0,0,0,0,1,0,0,0, 0,0,0,0,1,0,0,0, 0,0,0,0,1,0,0,0, 0,0,0,0,1,0,0,0, 0,0,0,0,1,0,0,0, 0,0,0,0,1,0,0,0, 0,0,0,1,0,0,0,0, 0,0,0,0,1,0,0,0 ],
perc => [ 0,0,0,1,0,0,0,0, 0,0,1,0,0,1,0,0, 0,0,0,1,0,0,0,0, 0,0,1,0,0,1,0,0, 0,0,0,1,0,0,0,0, 0,0,1,0,0,1,0,0, 0,0,0,1,0,0,0,0, 0,0,1,0,0,1,0,0, ],
c_hat1 => [ 1,0,1,1,1,1,0,1, 1,0,1,1,1,1,0,0, 0,0,1,1,1,1,1,1, 1,1,1,1,1,1,0,0, 1,0,1,1,1,1,0,1, 1,0,1,1,1,1,1,0, 1,0,1,1,1,1,1,1, 1,0,1,1,1,1,1,0 ],
);
my $bpm = 88;
my $synth = Sound::NeSynth->new();
$synth->render({
bpm => $bpm, # beats per minute
beats => [
{ seq => $patterns{kick}, tone => $kick, vol => 0.98 },
{ seq => $patterns{snr1}, tone => $snr1, vol => 0.45 },
{ seq => $patterns{perc}, tone => $perc, vol => 0.03 },
{ seq => $patterns{c_hat1}, tone => $c_hat, vol => 0.08 },
],
swing => 0.33,
});
use Audio::PortAudio;
my ( $sample_rate, $frames_per_buffer, $stream_flags ) = ( 44100, 512, undef );
my $api = Audio::PortAudio::default_host_api();
printf STDERR "Going to play via %s\nCtrl+c to stop...", $api->name;
my $device = $api->default_output_device;
my $stream = $device->open_write_stream( {
channel_count => 2,
sample_format => 'float32'
},
$sample_rate,
$frames_per_buffer,
$stream_flags,
);
my $length = (44100 * 60 / $bpm) * 16;
my $idx = 0;
my $delay_buffer = [];
my $delay_len = 44100 * 60 / $bpm * 0.492;
my $delay_idx = 0;
my $delay_feedback = 0.18;
# Infinite loop...
while (1) {
my @buffer_ary;
my @right;
my $i = 0;
my $wa = $stream->write_available;
for ( 0..$wa - 1 ) {
my $v = $synth->{samples_ref}[$idx] || 0.0;
$v += ( $delay_buffer->[$delay_idx] || 0.0 ) * $delay_feedback;
$delay_buffer->[$delay_idx] = $v;
$delay_idx = ($delay_idx + 1) % $delay_len;
# write both left and right channel
$buffer_ary[$i++] = $v;
$buffer_ary[$i++] = $v;
$idx = ( $idx + 1 ) % $length;
}
my $buffer = pack("f*", @buffer_ary);
$stream->write($buffer);
}
__END__
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment