Class: SynthBlocks::Fx::Chorus

Inherits:
Object
  • Object
show all
Defined in:
lib/synth_blocks/fx/chorus.rb

Overview

A simple chorus

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(sample_rate, phase: 0.0, rate: 0.5, delay_time: 7.0, mix: 0.5) ⇒ Chorus

Create new Chorus instance

phase allows you to shift the phase of the delayed signal additionally

rate is the LFO rate in Hz

delay_time is the maximum delay time in ms

mix is the ratio between original and delayed signal. 1.0 would mean only delayed signal (which wouldn’t make any sense)



21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
# File 'lib/synth_blocks/fx/chorus.rb', line 21

def initialize(sample_rate, phase: 0.0, rate: 0.5, delay_time: 7.0, mix: 0.5)
  @sample_rate = sample_rate
  @rate = rate
  @delay_time = delay_time
  @mix = mix

  @z1 = 0.0
  @sign = 0
  @lfo_phase = phase * 2.0 - 1.0
  @lfo_step_size = (4.0 * @rate / @sample_rate)
  @lfo_sign = 1.0

  # Compute required buffer size for desired delay and allocate it
  # Add extra point to aid in interpolation later
  @delay_line_length = ((@delay_time * @sample_rate * 0.001).floor * 2).to_i
  @delay_line = [0.0] * @delay_line_length
  @write_ptr = @delay_line_length - 1
  @lp = SynthBlocks::Core::OnePoleLP.new
  @output = 0.0
end

Instance Attribute Details

#delay_time=(value) ⇒ Object (writeonly)

:nodoc:



9
10
11
# File 'lib/synth_blocks/fx/chorus.rb', line 9

def delay_time=(value)
  @delay_time = value
end

#mix=(value) ⇒ Object (writeonly)

:nodoc:



9
10
11
# File 'lib/synth_blocks/fx/chorus.rb', line 9

def mix=(value)
  @mix = value
end

#phase=(value) ⇒ Object (writeonly)

:nodoc:



9
10
11
# File 'lib/synth_blocks/fx/chorus.rb', line 9

def phase=(value)
  @phase = value
end

#rate=(value) ⇒ Object (writeonly)

:nodoc:



9
10
11
# File 'lib/synth_blocks/fx/chorus.rb', line 9

def rate=(value)
  @rate = value
end

Instance Method Details

#run(input) ⇒ Object

run the chorus



44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
# File 'lib/synth_blocks/fx/chorus.rb', line 44

def run(input)
  # Get delay time
  offset = (next_lfo() * 0.3 + 0.4) * @delay_time * @sample_rate * 0.001

  # Compute the largest read pointer based on the offset.  If ptr
  # is before the first delayline location, wrap around end point
  ptr = @write_ptr - offset.floor;
  ptr += @delay_line_length - 1 if ptr < 0


  ptr2 = ptr - 1
  ptr2 += @delay_line_length - 1 if ptr2 < 0

  frac = offset - offset.floor.to_f
  @output = @delay_line[ptr2] + @delay_line[ptr] * (1.0 - frac) - (1.0 - frac) * @z1
  @z1 = @output

  # Low pass
  @lp.run(@output, 0.95)

  # Write the input sample and any feedback to delayline
  @delay_line[@write_ptr] = input

  # Increment buffer index and wrap if necesary
  @write_ptr += 1
  @write_ptr = 0 if @write_ptr >= @delay_line_length
  return (@output * @mix) + (input * (1.0-@mix))
end