ruby-libsamplerate 0.0.1

Sign up to get free protection for your applications and to get access to all the features.
data/.gitignore ADDED
@@ -0,0 +1,20 @@
1
+ *.gem
2
+ *.rbc
3
+ .bundle
4
+ .config
5
+ .yardoc
6
+ InstalledFiles
7
+ _yardoc
8
+ coverage
9
+ doc/
10
+ lib/bundler/man
11
+ pkg
12
+ rdoc
13
+ spec/reports
14
+ test/tmp
15
+ test/version_tmp
16
+ tmp
17
+
18
+ ._*
19
+ .DS_Store
20
+ *.sublime-*
data/.rvmrc ADDED
@@ -0,0 +1 @@
1
+ rvm use default@resample
data/Gemfile ADDED
@@ -0,0 +1,7 @@
1
+ source 'https://rubygems.org'
2
+
3
+ # Specify your gem's dependencies in resample.gemspec
4
+ gemspec
5
+
6
+ # Development only
7
+ gem "resample", :path => "."
data/Gemfile.lock ADDED
@@ -0,0 +1,19 @@
1
+ PATH
2
+ remote: .
3
+ specs:
4
+ resample (0.0.1)
5
+ ffi
6
+
7
+ GEM
8
+ remote: https://rubygems.org/
9
+ specs:
10
+ ffi (1.7.0)
11
+ rake (10.0.4)
12
+
13
+ PLATFORMS
14
+ ruby
15
+
16
+ DEPENDENCIES
17
+ bundler (~> 1.3)
18
+ rake
19
+ resample!
data/LICENSE.txt ADDED
@@ -0,0 +1,22 @@
1
+ Copyright (c) 2013 Elliott Williams
2
+
3
+ MIT License
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining
6
+ a copy of this software and associated documentation files (the
7
+ "Software"), to deal in the Software without restriction, including
8
+ without limitation the rights to use, copy, modify, merge, publish,
9
+ distribute, sublicense, and/or sell copies of the Software, and to
10
+ permit persons to whom the Software is furnished to do so, subject to
11
+ the following conditions:
12
+
13
+ The above copyright notice and this permission notice shall be
14
+ included in all copies or substantial portions of the Software.
15
+
16
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
17
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
18
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
19
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
20
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
21
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
22
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,29 @@
1
+ # Resample
2
+
3
+ TODO: Write a gem description
4
+
5
+ ## Installation
6
+
7
+ Add this line to your application's Gemfile:
8
+
9
+ gem 'resample'
10
+
11
+ And then execute:
12
+
13
+ $ bundle
14
+
15
+ Or install it yourself as:
16
+
17
+ $ gem install resample
18
+
19
+ ## Usage
20
+
21
+ TODO: Write usage instructions here
22
+
23
+ ## Contributing
24
+
25
+ 1. Fork it
26
+ 2. Create your feature branch (`git checkout -b my-new-feature`)
27
+ 3. Commit your changes (`git commit -am 'Add some feature'`)
28
+ 4. Push to the branch (`git push origin my-new-feature`)
29
+ 5. Create new Pull Request
data/Rakefile ADDED
@@ -0,0 +1 @@
1
+ require "bundler/gem_tasks"
@@ -0,0 +1,33 @@
1
+ require "ffi"
2
+ require "ruby-libsamplerate/data"
3
+ require "ruby-libsamplerate/simple"
4
+ require "ruby-libsamplerate/resample"
5
+ require "ruby-libsamplerate/convert"
6
+ require "ruby-libsamplerate/src_error"
7
+ require "ruby-libsamplerate/version"
8
+
9
+ module SRC
10
+ extend FFI::Library
11
+
12
+ ffi_lib 'libsamplerate'
13
+
14
+ SRC_SINC_BEST_QUALITY = 0
15
+ SRC_SINC_MEDIUM_QUALITY = 1
16
+ SRC_SINC_FASTEST = 2
17
+ SRC_ZERO_ORDER_HOLD = 3
18
+ SRC_LINEAR = 4
19
+
20
+
21
+
22
+ attach_function :src_simple, [:pointer, :int, :int], :int
23
+ attach_function :src_new, [:int, :int, :pointer], :pointer
24
+ attach_function :src_delete, [:pointer], :pointer
25
+ attach_function :src_process, [:pointer, :pointer], :int
26
+ attach_function :src_reset, [:pointer], :int
27
+ attach_function :src_set_ratio, [:pointer, :double], :int
28
+ attach_function :src_short_to_float_array, [:pointer, :pointer, :int], :void
29
+ attach_function :src_float_to_short_array, [:pointer, :pointer, :int], :void
30
+ attach_function :src_int_to_float_array, [:pointer, :pointer, :int], :void
31
+ attach_function :src_float_to_int_array, [:pointer, :pointer, :int], :void
32
+ attach_function :src_strerror, [:int], :pointer
33
+ end
@@ -0,0 +1,36 @@
1
+ module SRC
2
+ class Convert
3
+ def self.short_to_float(data)
4
+ base_convert data, :short, :float
5
+ end
6
+
7
+ def self.float_to_short(data)
8
+ base_convert data, :float, :short
9
+ end
10
+
11
+ def self.int_to_float(data)
12
+ base_convert data, :int16, :float
13
+ end
14
+
15
+ def self.float_to_int(data)
16
+ base_convert data, :float, :int16
17
+ end
18
+
19
+ private
20
+
21
+ def self.base_convert(data, in_type, out_type)
22
+ size = data.size
23
+ input = FFI::MemoryPointer.new in_type, size
24
+
25
+ write_ar = input.method "write_array_of_#{in_type}".to_sym
26
+ write_ar.call data
27
+
28
+ output = FFI::MemoryPointer.new out_type, size
29
+ converter = SRC.method "src_#{in_type}_to_#{out_type}_array"
30
+ converter.call input, output, size
31
+
32
+ read_ar = output.method "read_array_of_#{out_type}".to_sym
33
+ read_ar.call size
34
+ end
35
+ end
36
+ end
@@ -0,0 +1,12 @@
1
+ module SRC
2
+ class Data < FFI::Struct
3
+ layout :data_in, :pointer,
4
+ :data_out, :pointer,
5
+ :input_frames, :long,
6
+ :output_frames, :long,
7
+ :input_frames_used, :long,
8
+ :output_frames_gen, :long,
9
+ :end_of_input, :int,
10
+ :src_ratio, :double
11
+ end
12
+ end
@@ -0,0 +1,53 @@
1
+ module SRC
2
+ class Resample
3
+ attr_accessor :input_rate, :output_rate, :channels
4
+
5
+ def initialize(input_rate, output_rate, channels=1, type=SRC_SINC_FASTEST)
6
+ @input_rate = input_rate
7
+ @output_rate = output_rate
8
+ @channels = channels
9
+
10
+ error = FFI::MemoryPointer.new :int, 1
11
+ @state = SRC.src_new type, channels, error
12
+ end
13
+
14
+ def src_ratio
15
+ @output_rate.to_f / @input_rate.to_f
16
+ end
17
+
18
+ def process(data)
19
+ size = data.size
20
+ frames = size / @channels
21
+ rs_frames = (frames * src_ratio).to_i
22
+ rs_size = rs_frames * @channels
23
+
24
+ input = FFI::MemoryPointer.new :float, size
25
+ output = FFI::MemoryPointer.new :float, rs_size
26
+ input.write_array_of_float data
27
+
28
+ src_data = Data.new
29
+ src_data[:data_in] = input
30
+ src_data[:input_frames] = frames
31
+ src_data[:data_out] = output
32
+ src_data[:output_frames] = rs_frames
33
+ src_data[:src_ratio] = src_ratio
34
+ src_data[:end_of_input] = 0
35
+
36
+ res = SRC.src_process @state, src_data
37
+
38
+ raise SRCError.from_int res unless res == 0
39
+
40
+ frames_written = src_data[:output_frames_gen]
41
+ src_data[:data_out].read_array_of_float frames_written * @channels
42
+ end
43
+
44
+ def reset
45
+ SRC.src_reset @state
46
+ end
47
+
48
+ def destroy
49
+ SRC.src_delete @state
50
+ end
51
+
52
+ end
53
+ end
@@ -0,0 +1,43 @@
1
+ module SRC
2
+ class Simple
3
+ attr_accessor :input_rate, :output_rate, :channels
4
+
5
+ def initialize(input_rate, output_rate, channels)
6
+ @input_rate = input_rate
7
+ @output_rate = output_rate
8
+ @channels = channels
9
+ end
10
+
11
+ def src_ratio
12
+ @output_rate.to_f / @input_rate.to_f
13
+ end
14
+
15
+ def resample(data)
16
+ size = data.size
17
+ frames = size / @channels
18
+ rs_frames = (frames * src_ratio).to_i
19
+ rs_size = rs_frames * @channels
20
+
21
+ input = FFI::MemoryPointer.new :float, size
22
+ output = FFI::MemoryPointer.new :float, rs_size
23
+ input.write_array_of_float data
24
+
25
+ src = Data.new
26
+ src[:data_in] = input
27
+ src[:input_frames] = frames
28
+ src[:data_out] = output
29
+ src[:output_frames] = rs_frames
30
+ src[:src_ratio] = src_ratio
31
+
32
+
33
+ res = SRC.src_simple src, SRC::SRC_SINC_FASTEST, @channels
34
+
35
+ raise SRCError.from_int res unless res == 0
36
+
37
+
38
+ frames_written = src[:output_frames_gen]
39
+ src[:data_out].read_array_of_float frames_written * @channels
40
+ end
41
+
42
+ end
43
+ end
@@ -0,0 +1,13 @@
1
+ module SRC
2
+
3
+ class SRCError < StandardError
4
+ def self.from_int(code)
5
+ strerror = SRC.src_strerror code
6
+ SRCError.new strerror.get_string 0
7
+ end
8
+
9
+ def self.from_pointer(ptr)
10
+ self.from_int ptr.read_int
11
+ end
12
+ end
13
+ end
@@ -0,0 +1,3 @@
1
+ module SRC
2
+ VERSION = "0.0.1"
3
+ end
@@ -0,0 +1,25 @@
1
+ # coding: utf-8
2
+ lib = File.expand_path('../lib', __FILE__)
3
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
+ require 'ruby-libsamplerate/version'
5
+
6
+ Gem::Specification.new do |spec|
7
+ spec.name = "ruby-libsamplerate"
8
+ spec.version = SRC::VERSION
9
+ spec.authors = ["Elliott Williams"]
10
+ spec.email = ["e@elliottwillia.ms"]
11
+ spec.description = %q{Ruby binding for libsamplerate (aka "Secret Rabbit Code"). libsamplerate is an audio sample rate converter -- it adjusts the sample rate of raw audio.}
12
+ spec.summary = %q{Ruby binding for libsamplerate, an audio resampling library.}
13
+ spec.homepage = "http://github.com/elliottwilliams/ruby-libsamplerate"
14
+ spec.license = "MIT"
15
+
16
+ spec.files = `git ls-files`.split($/)
17
+ spec.executables = spec.files.grep(%r{^bin/}) { |f| File.basename(f) }
18
+ spec.test_files = spec.files.grep(%r{^(test|spec|features)/})
19
+ spec.require_paths = ["lib"]
20
+
21
+ spec.add_development_dependency "bundler", "~> 1.3"
22
+ spec.add_development_dependency "rake"
23
+
24
+ spec.add_runtime_dependency "ffi"
25
+ end
data/tests/test.rb ADDED
@@ -0,0 +1,16 @@
1
+ require "resample"
2
+ r = Resample::Simple.new 44100, 48000, 1
3
+
4
+ # def read_file(size)
5
+ # File.open("/Users/herooftime/Desktop/gang-44k-raw.pcm") do |file|
6
+ # while (buffer = file.read(size)) do
7
+ # yield buffer
8
+ # end
9
+ # end
10
+ # end
11
+
12
+ out = File.open "/Users/herooftime/Desktop/gang-out.pcm", "w+"
13
+
14
+ out.syswrite r.resample IO.read("/Users/herooftime/Desktop/gang-44k-raw.pcm")
15
+
16
+ puts "Allah done."
data/tests/test2.rb ADDED
@@ -0,0 +1,38 @@
1
+ require "ruby-libsamplerate"
2
+
3
+ fil = IO.read("/Users/herooftime/Desktop/ferg-mono.pcm")
4
+ ar = fil.unpack("s*")
5
+ puts ar.size
6
+
7
+ # zeroes = 0
8
+ # ar.each { |sample| zeroes+=1 if sample == 0.0 }
9
+ # puts "zeroes: #{zeroes}"
10
+
11
+ far = SRC::Convert.short_to_float ar
12
+ puts far.size
13
+
14
+ r = SRC::Simple.new 44100, 48000, 1
15
+ rs = r.resample far
16
+ puts rs.size
17
+
18
+ srs = SRC::Convert.float_to_short rs
19
+
20
+ # puts rs.length
21
+ # zeroes = 0
22
+ # rs.each { |sample| zeroes+=1 if sample == 0.0 }
23
+ # puts "zeroes: #{zeroes}"
24
+
25
+ out = File.open("/Users/herooftime/Desktop/re-out-raw.pcm", "w+")
26
+
27
+ mono_data = Array.new
28
+ srs.each_index do |i|
29
+ if i % 2 == 0
30
+ left = srs[i]
31
+ right = srs[i+1]
32
+ # mono_data << (right/2 - left/2) if left && right
33
+ mono_data << left
34
+ end
35
+ end
36
+
37
+ out.syswrite mono_data.pack("s*")
38
+ out.close
data/tests/test3.rb ADDED
@@ -0,0 +1,20 @@
1
+ require "ruby-libsamplerate"
2
+
3
+ fil = File.open("/Users/herooftime/Desktop/ferg.pcm")
4
+ out = File.open("/Users/herooftime/Desktop/re-out-raw.pcm", "w+")
5
+ r = SRC::Resample.new 44100, 48000, 2
6
+
7
+ size_of_10ms = (44100 / 100) * 2
8
+
9
+ while (buffer = fil.read(size_of_10ms)) do
10
+ data = buffer.unpack("s*")
11
+ data_f = SRC::Convert.short_to_float data
12
+
13
+ rs = r.process data_f
14
+ srs = SRC::Convert.float_to_short rs
15
+
16
+ out.syswrite srs.pack("s*")
17
+ end
18
+
19
+ fil.close
20
+ out.close
metadata ADDED
@@ -0,0 +1,113 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: ruby-libsamplerate
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.1
5
+ prerelease:
6
+ platform: ruby
7
+ authors:
8
+ - Elliott Williams
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+ date: 2013-04-15 00:00:00.000000000 Z
13
+ dependencies:
14
+ - !ruby/object:Gem::Dependency
15
+ name: bundler
16
+ requirement: !ruby/object:Gem::Requirement
17
+ none: false
18
+ requirements:
19
+ - - ~>
20
+ - !ruby/object:Gem::Version
21
+ version: '1.3'
22
+ type: :development
23
+ prerelease: false
24
+ version_requirements: !ruby/object:Gem::Requirement
25
+ none: false
26
+ requirements:
27
+ - - ~>
28
+ - !ruby/object:Gem::Version
29
+ version: '1.3'
30
+ - !ruby/object:Gem::Dependency
31
+ name: rake
32
+ requirement: !ruby/object:Gem::Requirement
33
+ none: false
34
+ requirements:
35
+ - - ! '>='
36
+ - !ruby/object:Gem::Version
37
+ version: '0'
38
+ type: :development
39
+ prerelease: false
40
+ version_requirements: !ruby/object:Gem::Requirement
41
+ none: false
42
+ requirements:
43
+ - - ! '>='
44
+ - !ruby/object:Gem::Version
45
+ version: '0'
46
+ - !ruby/object:Gem::Dependency
47
+ name: ffi
48
+ requirement: !ruby/object:Gem::Requirement
49
+ none: false
50
+ requirements:
51
+ - - ! '>='
52
+ - !ruby/object:Gem::Version
53
+ version: '0'
54
+ type: :runtime
55
+ prerelease: false
56
+ version_requirements: !ruby/object:Gem::Requirement
57
+ none: false
58
+ requirements:
59
+ - - ! '>='
60
+ - !ruby/object:Gem::Version
61
+ version: '0'
62
+ description: Ruby binding for libsamplerate (aka "Secret Rabbit Code"). libsamplerate
63
+ is an audio sample rate converter -- it adjusts the sample rate of raw audio.
64
+ email:
65
+ - e@elliottwillia.ms
66
+ executables: []
67
+ extensions: []
68
+ extra_rdoc_files: []
69
+ files:
70
+ - .gitignore
71
+ - .rvmrc
72
+ - Gemfile
73
+ - Gemfile.lock
74
+ - LICENSE.txt
75
+ - README.md
76
+ - Rakefile
77
+ - lib/ruby-libsamplerate.rb
78
+ - lib/ruby-libsamplerate/convert.rb
79
+ - lib/ruby-libsamplerate/data.rb
80
+ - lib/ruby-libsamplerate/resample.rb
81
+ - lib/ruby-libsamplerate/simple.rb
82
+ - lib/ruby-libsamplerate/src_error.rb
83
+ - lib/ruby-libsamplerate/version.rb
84
+ - ruby-libsamplerate.gemspec
85
+ - tests/test.rb
86
+ - tests/test2.rb
87
+ - tests/test3.rb
88
+ homepage: http://github.com/elliottwilliams/ruby-libsamplerate
89
+ licenses:
90
+ - MIT
91
+ post_install_message:
92
+ rdoc_options: []
93
+ require_paths:
94
+ - lib
95
+ required_ruby_version: !ruby/object:Gem::Requirement
96
+ none: false
97
+ requirements:
98
+ - - ! '>='
99
+ - !ruby/object:Gem::Version
100
+ version: '0'
101
+ required_rubygems_version: !ruby/object:Gem::Requirement
102
+ none: false
103
+ requirements:
104
+ - - ! '>='
105
+ - !ruby/object:Gem::Version
106
+ version: '0'
107
+ requirements: []
108
+ rubyforge_project:
109
+ rubygems_version: 1.8.25
110
+ signing_key:
111
+ specification_version: 3
112
+ summary: Ruby binding for libsamplerate, an audio resampling library.
113
+ test_files: []