Is it possible to shorten the ringvector ".rotate()" to ".r()"?

I like to shorten “spread” function to “s” with define

define :s do |a,b|
  spread(a,b)
end

live_loop :a1 do
  tick
  sample :bd_fat, amp: 2 if s(3,7).rotate(2).look
  sleep 0.25
end  

is it possible to shorten “.rotate()” to “.r()”?

I have tried

define :s do |a,b|
  spread(a,b)
end

define :r do |c|
  rotate(c)
end

live_loop :a1 do
  tick
  sample :bd_fat, amp: 2 if s(3,7).r(2).look
  sleep 0.25
end

but “.rotate()” is a ringvector that affects spread(), so it’s doesn’t work.


I would like to use the notation above since I find it more clear to read.
But we could write it as one function

define :s do |a,b, *args|  # with optinal parameter on r for rotate
  #                          Both notations now work fx s(3,7) or s(3,7,0)
  #                          Mister Bomb - Sonic Pi Tutorial - Adding Default and Optional Parameters to Functions
  #                          https://youtu.be/RpiWumugXrY?feature=shared&t=430
  r = 0
  r = args[0] if args.length == 1 # only looking for 1 value in args[] array
  
  spread(a,b).rotate(r)
end
live_loop :a1 do
  tick
#  sample :bd_fat, amp: 2 if s(3,7).look   # works with default value 0
  sample :bd_fat, amp: 2 if s(3,7,0).look
  sample :bd_fat, amp: 4, rpitch: 36 if s(3,7,2).look
  sleep 0.25
end

Hmm I guess I just have to get use to doing it like this since it’s less typing.

You have to add the method on to the RingVector class, which you can do like this:

class SonicPi::Core::RingVector
  def r(n)
    self.rotate(n)
  end
end

define :s do |a,b|
  spread(a,b)
end

puts s(3,8).r(2)

Note that this is using implementation details of Sonic Pi, so is not strictly supported, and could break in a future version.

1 Like