ruby-libsamplerate 0.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
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: []