Idea For A Nice Live Looper

Note: Development of Cells Device has ceased (it was only a test). The live performance capabilities have been developed into Cells!. The Glitch like features may occur in the future as a separate tool.

Early alpha version attached. This is how it works:

  • The current pattern is divided into beats (quarter notes).
  • Each beat is subdivided into 2, 4 or 8 sub-beats
  • You indicate instruments you want to use with this tool by adding “[L]” into their name
  • Select one of these instruments before starting the tool
  • Tools -> Cell Device -> 2 / 4 or 8 PPQN
  • The GUI will magically appear if everythings ok and playback will start
  • The pattern is looped and the current track cleared
  • Playback position is highlighted in green
  • Click a cell command and click cells (red = mute, blue = reverse, yellow = repeat the previous cell)
  • Operations on cells are not commutative
  • Select different loops in realtime with the buttons on the left, the same cell commands will be applied
  • You can also change the BPM if you wish

I have an example file with some loops ready for use here


All feedback welcome!

very cool stuff!

Had a bug, entered in a bunch of different colored blocks, jamming and previewing different instruments, while switching to bodycount, I got:

edit: chose 8 ppqn when opening the tool for the first time.

Yes, it can struggle sometimes to keep up (it is version 0.1!).

I suggest working at less ppqn for now.


edit: initialized the tool with ppqn of 4, but upped the lbp to 8 as the loop didn’t sound right, colored a bunch of blocks and received notice, so probably the same struggling to keep up as the previous bug.


Opened up a second instance of yer tool on an empty track, got a message first that the loop didn’t fit the pattern if I remember correctly, then when I closed that particular notice, this error message popped up. Also noticed the tools stopped highlighting the blocks while the pattern is running.


I really need information about what you were doing at the time, what the settings were etc. to identify these bugs.

Have updated the previous posts.

Feature request:

a button to clear all cells, and have the right mouse button blacken/make normal a cell.

nice start mxb… looks promising !

what about using keyboard to change loops on the fly ?

Really cool stuff, mxb!
No bug reports from me (apart from the one Jonas already posted [std::logic_error: 'trying to access a no longer available pattern_line note column.]).

Yeah, I’m trying to do this right clicking all the time since I started testing!

Opened up a tool instance, I think at 4 ppqn, listened to the loop, didn’t like the sound, closed the tool, and tried opening up a new instance of the tool at a higher ppqn of 8, got the following notice:


  • after this bug, I tried opening a second tool instance for a neighbor track, trying to layer sounds.

I think trying to create a second tool instance for another tracks has messed up the already initialized tool, running the original tool now adds the events in the other track, no matter where the cursor resides. Got the following bug notice when deleting all tracks in the song but the first used track, and running the script:

Sorry for the confusing descriptions, I need sleep.

Just you wait till someone posts a video of the Zyklus MPS hardware and requests that.

I have a little question about this. It’s nice to use a GUI like this to modify a sample that is playing. Can these variations of a loop be committed into the pattern as pattern-data? Can these be “read” from the current pattern, modified and written back in? Would I be able to have 10 patterns which all use the same drumbeat, but each pattern having a different bunch of colored tiles and then ditch the whole GUI/script and still retain the modifications in the patterns themselves?

since the API allows for offline/realtime rendering, could this modification of a beat also be rendered into a new instrument as a loop? will i be able to use the GUI to switch between this newly-rendered-sample and the previous-unmodified-sample, without having to close & re-open the GUI?

could this also be used in such a way that you already have a drum pattern ready, and just import that to the GUI and then be able to control which drumhits are reversed and which aren’t, without the gui caring that it’s a 512 row pattern and there’s about 43 drumhits overall in a certain track of the pattern, so the gui would show 43 buttons ( just as an example ).

also, could there be an easy cloning method where if you have a nice 16 cell beat going, you might want to enlarge the gui to 32 cells and copy the 1-16 cells to 17-32 cells to make some additional modifications and then dump this stuff back to the patterndata? so a 16 row pattern would become a 32 row pattern in light of this modification? or the second 16 rows would be placed to the next pattern? (so patterns could be, for instance, 48 rows in length, but the beat you’re modifying over the course of the whole song is a 32 row/cell beat, and it just keeps playing over the course of the whole song, so first 32 rows would be played 1-31, then the next 32 rows would be played 32-48-15 … etc. for more fluid drumprogramming? i think this is somewhat similar to what Joule was thinking of doing a while ago (with pattern templates or what was his name for it… instrument table? anyway…))

is there a good n.o.w. video where you show the stuff that hasn’t dawned on it’s users, please?

but yes, a workflow “done right” will change quite a bit, and in non-obvious ways, too!

feature request: when changing from pattern1 to pattern2, update the gui to conform to pattern2 stuff, i.e. if you open the gui once, it follows your selected track + selected pattern, and changes accordingly to which pattern you are in (i dont much care about which track you’re in, cos that’s a completely different can of worms)

btw, maybe just a status line in the gui which says which pattern you are editing. maybe that’s easier to do than auto-read.

i see that a 4ppqn some cells will sometimes end up (at 114bpm) staying green even if they shouldn’t.

i’m trying to replicate the notifier bugs i’m getting but not sure how to get them going, it seems related to clicking the cell that’s already playing, and also i went and did a hatchet job on the pattern data by deleting random notes and lines and sometimes i get a notifier error when it’s trying to access a note column which has no data in it (or something). i’m trying to make this wreck up in replicable ways but so far no luck :confused:

okay, if you have the gui open and create a new song, and close the gui and run 4ppqn, you’ll constantly get an error such as this:

std::logic_error: 'trying to access a no longer available pattern_line note column.'  
stack traceback:  
 [C]: ?  
 [C]: in function '__index'  
 [string "do..."]:12: in function   
 ./actions.lua:60: in function 'update_cell_in_pattern'  
 ./actions.lua:36: in function 'populate_pattern_with_defaults'  
 main.lua:82: in function 'start_celldevice'  
 main.lua:111: in function <111><br>```

one more request: please provide a way of opening the gui up (i get an error after it slices up a sample to the pattern, and then can't actually ignore the error and start slamming in reverses, repeats etc.<br>
ok, closing a 512 row pattern resultant 4ppqn gui will actually kill renoise <img src="" class="bbc_emoticon" alt=":)"></111>

This was the result of running the 4ppqn thing a couple of times (first at 32 rows, then 64, then 128, then 256) - i finally got it to start chopping, only for it to then die in the middle of it.

it’s not an amazingly complex wav or anything. so i decided to just ditch the auto-slicing and just use this little script which chops the sample to either 4 slices, 8, 16 or 32 slices…
so, after re-slicing to 16 equal parts, i ran the 4ppqn only to get loads and loads of rows full of the loop. the gui opens, i switch to 64 rows (that’s all i need of the loop to hear all of it, the rest seemed useless extra info and some silences, too) - only to realize i have no way of refreshing the gui to only show 64 rows worth of stuff instead of the 256 rows i needed to have to be able to chop them.

another one, if there’s a bunch of mutes in cells (note-off in the pattern-data, it seems) and you start slapping in repeats on those cells, the note off will stay there, instead of being killed off by the logic of “cell has mute cell has trigger -> trigger takes presedence and pattern-row column is reset to the actual note instead of noteoff”
btw, while playback was on, i was clicking in some triggers and got the same note_column not there error, which was weird (i had 8 cells with mute, and was clicking in trigger to each of the 8 cells and one of them shot me the error)… i still can’t seem to figure out where the notecolumn not there error even comes from.

Whoa, lots of feedback. In order…

Thanks for the updated information, it makes things much much easier.

The ViewBuilder API cannot identify right click events so that is not possible. However, a global reset button can be implemented.

Agree. Prev/Next loop buttons plus make them all midi mappable are on the GUI improvements list.

The tool doesn’t like being opened more than once at the moment. Eventually this will be worked out. However, for now, I’ll restrict it to one open at a time.

Also, track change hooks are not yet implemented, so it will crash if you add/remove tracks / start a new song etc. while the GUI is open. It’s pretty fragile at the moment.

Seems feasible to be honest.

That is how it works currently. The changes to the cells write to the current pattern.

Eventually, yes.

Sorry, don’t understand this.

Render modified pattern to new sample is planned. This could mute the original pattern track and replace with the rendered one if desired. Is this a general desire from everyone?

Not currently. Samples need to be sliced on beats for the current implementation.

Pattern length doubling could be implemented.

More feedback in the GUI is planned. This was just the absolute basics.

Sometimes the GUI runs too slowly. Optimisation is planned.

Not sure I understand? I can open the GUI again (after closing), but it will reset to normal playback currently.

Again, pattern change hooks are not currently implemented, but are planned. As is re-reading the current information from the pattern.

Also, slice markers must be placed on beats in the sample (not autosliced). I may implement an autoslice loop equally feature to make this easier from the GUI.

The operations are non commutative, i.e. the order of operations affects the result. Retrigger duplicates the previous cell, including it’s modifiers.

Thanks for all the feedback so far.

excellent. then you will of course be doing something similar to this:

[details=“Click to view contents”] ```

–Wipe all slices
function wipeslices()
local number=(table.count([currInst].samples[currSamp].slice_markers))

for i=1,number do[currInst].samples[currSamp]:delete_slice_marker(([currInst].samples[currSamp].slice_markers[1]))

function slicerough(changer)
local number=(table.count([currInst].samples[currSamp].slice_markers))[currInst].samples[currSamp].loop_mode=2[currInst].samples[currSamp].new_note_action=1

for i=1,number do[currInst].samples[currSamp]:delete_slice_marker(([currInst].samples[currSamp].slice_markers[1]))

for i=1,changer do[currInst].samples[currSamp]:insert_slice_marker(tw*i)

renoise.tool():add_midi_mapping{name=“Global:Paketti:Wipe&Create Slices (16) x[Toggle]”, invoke = function() slicerough(16) end}
renoise.tool():add_keybinding {name=“Global:Paketti:Wipe&Create Slices (4)”, invoke = function() slicerough(4) end}
renoise.tool():add_keybinding {name=“Global:Paketti:Wipe&Create Slices (8)”, invoke = function() slicerough(8) end}
renoise.tool():add_keybinding {name=“Global:Paketti:Wipe&Create Slices (16)”, invoke = function() slicerough(16) end}
renoise.tool():add_keybinding {name=“Global:Paketti:Wipe&Create Slices (32)”, invoke = function() slicerough(32) end}
renoise.tool():add_keybinding {name=“Global:Paketti:Wipe&Create Slices (64)”, invoke = function() slicerough(64) end}
renoise.tool():add_menu_entry {name=“Sample Editor:Paketti:Wipe&Create Slices (4)”, invoke = function() slicerough(4) end}
renoise.tool():add_menu_entry {name=“Sample Editor:Paketti:Wipe&Create Slices (8)”, invoke = function() slicerough(8) end}
renoise.tool():add_menu_entry {name=“Sample Editor:Paketti:Wipe&Create Slices (16)”, invoke = function() slicerough(16) end}
renoise.tool():add_menu_entry {name=“Sample Editor:Paketti:Wipe&Create Slices (32)”, invoke = function() slicerough(32) end}
renoise.tool():add_menu_entry {name=“Sample Editor:Paketti:Wipe&Create Slices (64)”, invoke = function() slicerough(64) end}
renoise.tool():add_menu_entry {name=“Sample Editor:Paketti:Wipe Slices”, invoke = function() wipeslices() end}

It's really simple, just slices your stuff to 4, 8, 16, 32 or 64 slices. i was surprised at how well these wipeslices worked with your looper script ![:)]( (and yes, i know you'll code it way better. just thought to paste anyway since it's already "ready" (for at least my uses) ) ![:)](   
-- in response to the rest of your replies: the 10 pattern thing was just to state that maybe one would like to be able to create multiple copies of one pattern which has been edited with the script, and then just duplicate that pattern, make the new pattern unique, and then be able to bring the GUI back up again for the next pattern or whichever pattern one has selected..  
about Zyklus MPS being feasible with LUA, well, maybe! but it would require so much groundwork (how to record pattern notes and be able to output them back again via nondestructive transposition (i suppose this could be gimmicked out of having a hidden pattern (99, for instance) which records the keys you wish to use, one track would be one "midi clip", so to speak, and then one could somehow transpose the midi clip content nondestructively, but how would the script tell the api to start playing these transposed results realtime? ![:)](  
render modified pattern, mute and insert new track + note to toggle the newly rendered instrument would probably be quite interesting! ![:)](  
btw, i was running into those notifier issues without changing track and without changing pattern. i'll try and hack at this further.  
[quote="mxb, post:36, topic:34313"]  
The operations are non commutative, i.e. the order of operations affects the result. Retrigger duplicates the previous cell, including it's modifiers.  
yes.. so if you have a regular cell 1, and the second cell has "mute, trigger", the mute takes precedence. i suppose it would be good for someone who firts reverses + retriggers bits of the loop, and while the jamming continues, he decides to start dropping mutes on top of sounds he doesn't want to hear later on. i guess if one were to click on Trigger twice on the same cell (which has a mute), the recognition of "wait, there's already a trigger there, i'll kick that mute off", would be weird or not something you'd like to think about right now? ![:)](

hi mxb. will you be able to add custom cell colours so that when the cell is “played”, a certain bunch of functions are run by the script?

Because then there could be a “start sampling” cell so one could start using the cellery to sample stuff with pattern-sync-ON, and then at the end of sampling one could then autoslice the sampled patternsync-sample, and then divide it into 4ppqn or something and off we go.

just throwing it out there since we already talked about the record-to-current-track scriptage a while ago :)