Sync loops in sequencer


#1

Hi, I am testing out Sonic Pi and I have been trying to find a way for creating a simple sequencer. I have looked at the sync manual but I would like to get some ideas of the best way of doing this.

If you listen to the code below, why are the chords loop skipping a bar? What will be the best strategy to create a sequencer?

(I also thought about having a main triggering every sixteenth note but that did not work well either)

use_bpm 120

live_loop :main do
  sample :elec_blip2
  sleep 4
end

live_loop :loop_chord do
  sync :main
  play :c4
  play :e4
  play :g4
  sleep 2
  play :f4
  play :a4
  play :c4
  sleep 2
end

#2

Hi @keys,

from time to time there are questions about the sync command similar to yours. Here is a link to such a discussion, which will probably help: First little diddy

Basically the sync will and can not sync to an event in the past. One way to cope with this in your case is to write your sync in the live_loop line such as

live_loop :loop_chord, sync: :main do
  # code goes here ...
end

But I recommend to read the linked thread and the material in the tutorial to understand more fully what actually is going on.

Martin


#3

Thank you for the advise. I tried to put sync in the upper line as you suggested but it still does not behave as I expect.

use_bpm 120

live_loop :main do
  sample :elec_blip2
  sleep 4
end

live_loop :loop_chord, sync: :main do
  sync :main
  play :c4
  play :e4
  play :g4
  sleep 2
  play :f4
  play :a4
  play :c4
  sleep 2
end

#4

I see. It seems you forgot to remove the second line in your second loop:

live_loop :loop_chord, sync: :main do
  sync :main # this one has to be removed
  play :c4
  # ...

#5

Ah that explains it :slight_smile: Thank you so much for the advise. It works fine now.


#6

I hope it is ok to add one more follow up question in this thread to clarify. In the code below the “metronome” wakes up “loop1” and the loop skips the first run as espected. But why is “loop2” started simultaniously as “loop1”? Shouldn’t “loop2” also wait for “loop1” to finish its first run?

live_loop :metronome do
  sleep 1
end

live_loop :loop1, sync: :metronome do
  #bar 1
  sample :elec_filt_snare
  sample :drum_bass_hard
  sleep 0.5
  sample :drum_bass_soft
  sleep 0.5
  
  #bar 2
  sample :elec_beep
  sample :drum_snare_hard
  sleep 1
  
  #bar 3
  sample :elec_beep
  sample :drum_bass_hard
  sleep 0.5
  sample :drum_bass_soft
  sleep 0.5
  
  #bar 4
  sample :elec_beep
  sample :drum_snare_hard
  sleep 0.5
  sample :drum_snare_hard
  sleep 0.5
end


live_loop :loop2, sync: :loop1 do
  #bar 1 to 8
  sample :elec_blip2
  16.times do
    sample :drum_cymbal_pedal
    sleep 0.5
  end
end

#7

Hi @keys,

I think it works like this: When you run metronome, both other live_loops will ‘start’ also (= code being evaluated), and ‘note’ to which live_loops they are told to listen to:

  • loop1 to metronome
  • loop2 to loop1

So as soon as loop1 starts loop2 also will start because it had already had time to sync. Maybe someone with more internal knowledge can explain that more accurately (or correct me) but I thing the sync command (positioned in the live_loop line) will be honored by another live_loop even if the first one is still waiting.