audite 0.1.6 → 0.2.0
Sign up to get free protection for your applications and to get access to all the features.
- data/README.md +8 -3
- data/audite.gemspec +1 -1
- data/ext/portaudio/portaudio.c +14 -8
- data/lib/audite.rb +10 -6
- metadata +1 -1
data/README.md
CHANGED
@@ -28,15 +28,15 @@ require 'audite'
|
|
28
28
|
player = Audite.new
|
29
29
|
|
30
30
|
player.events.on(:complete) do
|
31
|
-
|
31
|
+
puts "COMPLETE"
|
32
32
|
end
|
33
33
|
|
34
34
|
player.events.on(:level) do |level|
|
35
|
-
puts level
|
35
|
+
puts "LEVEL: #{level}"
|
36
36
|
end
|
37
37
|
|
38
38
|
player.events.on(:position_change) do |pos|
|
39
|
-
puts pos
|
39
|
+
puts "POSITION: #{pos} seconds"
|
40
40
|
end
|
41
41
|
|
42
42
|
player.load('test.mp3')
|
@@ -45,6 +45,11 @@ player.forward(20)
|
|
45
45
|
|
46
46
|
```
|
47
47
|
|
48
|
+
## Requirements
|
49
|
+
|
50
|
+
* Portaudio >= 19
|
51
|
+
* Mpg123 >= 1.14
|
52
|
+
|
48
53
|
## OSX Install
|
49
54
|
|
50
55
|
```
|
data/audite.gemspec
CHANGED
data/ext/portaudio/portaudio.c
CHANGED
@@ -51,7 +51,7 @@ static int paCallback(const void *inputBuffer,
|
|
51
51
|
return 0;
|
52
52
|
}
|
53
53
|
|
54
|
-
VALUE rb_portaudio_new(VALUE klass)
|
54
|
+
VALUE rb_portaudio_new(VALUE klass, VALUE framesPerBuffer)
|
55
55
|
{
|
56
56
|
PaStreamParameters outputParameters;
|
57
57
|
const PaDeviceInfo *deviceInfo;
|
@@ -63,16 +63,16 @@ VALUE rb_portaudio_new(VALUE klass)
|
|
63
63
|
pthread_mutex_init(&portaudio->mutex, NULL);
|
64
64
|
pthread_cond_init(&portaudio->cond, NULL);
|
65
65
|
|
66
|
-
portaudio->size =
|
66
|
+
portaudio->size = FIX2INT(framesPerBuffer) * 2;
|
67
67
|
portaudio->buffer = (float *) malloc(sizeof(float) * portaudio->size);
|
68
68
|
|
69
69
|
err = Pa_OpenDefaultStream(&portaudio->stream,
|
70
70
|
0, /* no input channels */
|
71
71
|
2, /* stereo output */
|
72
72
|
paFloat32, /* 32 bit floating point output */
|
73
|
-
44100, /*
|
74
|
-
|
75
|
-
paCallback,
|
73
|
+
44100, /* sample rate*/
|
74
|
+
FIX2INT(framesPerBuffer),
|
75
|
+
paCallback,
|
76
76
|
(void*) portaudio);
|
77
77
|
|
78
78
|
if (err != paNoError) {
|
@@ -96,13 +96,19 @@ VALUE portaudio_wait(void *ptr)
|
|
96
96
|
|
97
97
|
VALUE rb_portaudio_write(VALUE self, VALUE buffer)
|
98
98
|
{
|
99
|
-
int i;
|
99
|
+
int i, len;
|
100
100
|
Portaudio *portaudio;
|
101
101
|
Data_Get_Struct(self, Portaudio, portaudio);
|
102
102
|
|
103
103
|
Check_Type(buffer, T_ARRAY);
|
104
104
|
|
105
|
-
|
105
|
+
len = RARRAY_LEN(buffer);
|
106
|
+
|
107
|
+
if (len != portaudio->size) {
|
108
|
+
rb_raise(rb_eStandardError, "array length does not match buffer size: %d != %d", len, portaudio->size);
|
109
|
+
}
|
110
|
+
|
111
|
+
for (i = 0; i < len; i++) {
|
106
112
|
portaudio->buffer[i] = NUM2DBL(rb_ary_entry(buffer, i));
|
107
113
|
}
|
108
114
|
|
@@ -154,7 +160,7 @@ void Init_portaudio(void) {
|
|
154
160
|
|
155
161
|
rb_cPortaudio = rb_define_class("Portaudio", rb_cObject);
|
156
162
|
|
157
|
-
rb_define_singleton_method(rb_cPortaudio, "new", rb_portaudio_new,
|
163
|
+
rb_define_singleton_method(rb_cPortaudio, "new", rb_portaudio_new, 1);
|
158
164
|
rb_define_method(rb_cPortaudio, "write", rb_portaudio_write, 1);
|
159
165
|
rb_define_method(rb_cPortaudio, "start", rb_portaudio_start, 0);
|
160
166
|
rb_define_method(rb_cPortaudio, "stop", rb_portaudio_stop, 0);
|
data/lib/audite.rb
CHANGED
@@ -20,33 +20,37 @@ class Audite
|
|
20
20
|
|
21
21
|
attr_reader :events, :active
|
22
22
|
|
23
|
-
def initialize
|
23
|
+
def initialize(buffer_size = 2**14)
|
24
|
+
@buffer_size = buffer_size
|
24
25
|
@events = Events.new
|
25
|
-
@stream = Portaudio.new
|
26
|
+
@stream = Portaudio.new(@buffer_size)
|
26
27
|
@thread = start_thread
|
27
28
|
end
|
28
29
|
|
29
30
|
def start_thread
|
30
31
|
Thread.start do
|
31
32
|
loop do
|
32
|
-
@stream.write(process(
|
33
|
+
@stream.write(process(@buffer_size * 2))
|
33
34
|
end
|
34
35
|
end
|
35
36
|
end
|
36
37
|
|
38
|
+
def silence(samples)
|
39
|
+
Array.new(samples, 0)
|
40
|
+
end
|
41
|
+
|
37
42
|
def process(samples)
|
38
43
|
if tell >= length
|
39
44
|
stop_stream
|
40
45
|
events.trigger(:complete)
|
41
|
-
(
|
46
|
+
silence(samples)
|
42
47
|
|
43
48
|
elsif slice = read(samples)
|
44
49
|
events.trigger(:level, level(slice))
|
45
50
|
events.trigger(:position_change, position)
|
46
|
-
|
47
51
|
slice
|
48
52
|
else
|
49
|
-
(
|
53
|
+
silence(samples)
|
50
54
|
end
|
51
55
|
|
52
56
|
rescue => e
|