int32 offset
int32 clipslot
bool32.rising record
bool32 input
bool32 96ppq
bool32 bartrig
bool32 recbartrig
bool32 initrig
bool32 trigger
bool32 overdub
bool32 stop
bool32 clear
bool32 erase
int32 stepunQP
int32 stepunQR
int32 stepunQCC
int32 copy
int32 copyR
int32 barcount
int32 length
int32 tablesize
int32 erasenote
bool32 recshift
bool32 output
bool32 record
bool32 overdub
bool32 wait
bool32 full
bool32 reset
bool32 cleartrigger
objref table
spinner bar
spinner voices
spinner clipslots
spinner channel
combo output
int wait;
int voice;
int R;
int Rwait;
int prevclipslot;
int stepunQ;
int copyclock;
int qtrig;
int ocol;
int clipslot;
int prevfull;
int playslot;
int prevbrcount;
int RC;
int RCWait;
int clipoffs;
int ktrig;
int modetrig;
int RR;
int bendvoice;
int pct;
int currentdub;
int dubtrig;
int length;
int xtrighold;
int xtrigQ;
int lengthout;
int full;
int count;
int barcount;
int ptrig;
int recshift;
int otrig;
int retrig;
int rectrig;
int brtrig;
int strig;
int atrig;
int play;
int record;
int overdub;
int xtrig;
int total;
int ltrig;
int ertrig;
int ntrig;
int rtrig;
int budd;
int speed;
int clear;
int cleartrig;
int erasenote;
int erase;
int erasegate;
uint32_t i;
uint32_t ii;
uint32_t src;
uint32_t dst;
uint32_t range;
uint32_t block;
voice = ((attr_bar << 9) - ((attr_bar << 9) >> 2));
bendvoice = (voice * 5);
budd = ((voice + voice + voice) * attr_voices);
clear = 1;
prevclipslot = 0;
R = budd;
RC = budd;
clipslot = 0;
clipoffs = (attr_clipslots * (budd + bendvoice)) + budd + budd;
// stepunQ
if ((inlet_96ppq > 0) && !qtrig) {
stepunQ += 1;
copyclock += 1;
if (stepunQ == 13) {
copyclock = 0;
if (RCWait) {
RC = R;
RCWait = 0;
}
}
qtrig = 1;
} else if (!(inlet_96ppq > 0))
qtrig = 0;
if (inlet_clipslot != pct) {
if (inlet_bartrig) {
pct = inlet_clipslot;
ltrig = 1;
}
}
if (xtrigQ) {
stepunQ = 0;
barcount = 0;
length = 0;
}
if (inlet_initrig && !otrig) {
stepunQ = 48;
otrig = 1;
} else if (!inlet_initrig) {
otrig = 0;
}
if (inlet_active && !atrig) {
stepunQ = 0;
atrig = 1;
}
if (!inlet_active && atrig) {
atrig = 0;
ltrig = 1;
play = 0;
record = 0;
wait = 0;
}
if ((inlet_clipslot != prevclipslot) && (inlet_clipslot < (attr_clipslots))) {
prevfull = full;
Rwait = 1;
}
retrig = 0;
ltrig = 0;
xtrig = 0;
xtrigQ = 0;
full = attr_table.array[clipslot + clipoffs];
lengthout = full;
outlet_full = attr_table.array[inlet_clipslot + clipoffs];
if (inlet_overdub && !dubtrig) {
overdub = !overdub;
if (overdub) {
ocol = 9;
} else if (!overdub) {
ocol = 11;
}
currentdub = overdub;
dubtrig = 1;
}
if (!inlet_overdub) {
dubtrig = 0;
}
if (inlet_bartrig && !brtrig) {
brtrig = 1;
barcount += 1;
if (barcount > attr_bar) {
barcount = 0;
}
if (recshift) {
recshift = 0;
}
if (modetrig) {
modetrig = 0;
xtrigQ = 1;
}
if (xtrighold) {
xtrigQ = 1;
xtrighold = 0;
}
}
// }
if (!inlet_bartrig) {
brtrig = 0;
}
if (inlet_recbartrig && !rectrig) {
length += 1;
count += 1;
rectrig = 1;
if ((length >= lengthout) && (lengthout > 0)) {
length = 0;
xtrig = 1;
xtrighold = 1;
retrig = 1;
}
if (wait) {
wait = 0;
retrig = 1;
}
}
if (!inlet_recbartrig) {
rectrig = 0;
}
if (inlet_active) {
// stop
if (inlet_stop && !strig) {
strig = 1;
wait = 1;
}
// play/record
if (inlet_trigger && !ptrig && !strig &&
(inlet_clipslot < (attr_clipslots)) && (!inlet_clear) && !ktrig) {
if (record) {
attr_table.array[clipslot + clipoffs] = length + 1;
}
ptrig = 1;
wait = 1;
}
// record
if (inlet_record && !ptrig) {
attr_table.array[inlet_clipslot + clipoffs] = 0;
full = 0;
ptrig = 1;
wait = 1;
}
if (retrig && !strig) {
if (ptrig) {
R = (inlet_clipslot * (budd + bendvoice)) + budd;
RCWait = 1;
clipslot = inlet_clipslot;
full = attr_table.array[clipslot + clipoffs];
playslot = inlet_clipslot;
}
if ((full) && ptrig) {
length = 0;
play = 1;
record = 0;
ptrig = 0;
xtrig = 1;
xtrighold = 1;
prevclipslot = inlet_clipslot;
} else if (!full && ptrig) {
if (play || record) {
clear = 0;
cleartrig = 1;
ltrig = 1;
}
length = 0;
record = 1;
recshift = 1;
count = 0;
play = 0;
ptrig = 0;
xtrig = 1;
xtrighold = 1;
prevclipslot = inlet_clipslot;
}
}
}
if (strig && retrig) {
strig = 0;
play = 0;
record = 0;
}
// maxbar
if (record && (length == attr_bar)) {
attr_table.array[clipslot + clipoffs] = length;
xtrig = 1;
xtrighold = 1;
length = 0;
record = 0;
play = 1;
}
if (lengthout == 0) {
lengthout = attr_bar;
}
// save load clear
if (inlet_clipslot < (attr_clipslots)) {
if (inlet_clear && !ktrig) {
if (inlet_clipslot == playslot) {
play = 0;
record = 0;
}
ktrig = 1;
attr_table.array[inlet_clipslot + clipoffs] = 0;
clear = 0;
cleartrig = 1;
ltrig = 1;
ntrig = 1;
i = 0;
rtrig = 0;
// overdub=0;
}
if (!inlet_clear) {
ktrig = 0;
}
speed = 16 << 4;
range = budd;
block = (range / speed) * speed;
src = (inlet_clipslot * (budd + bendvoice)) + budd;
dst = (inlet_clipslot * (budd + bendvoice)) + budd;
if ((i == range) && (!inlet_trigger)) {
ntrig = 0;
i = 0;
clear = 1;
}
// copy n chunks of size 'speed'
if (ntrig && (i < block)) {
{
for (ii = 0; ii < speed; ii++)
attr_table.array[(i + ii + dst)] =
((attr_table.array[(i + ii + src)]) * (clear));
}
i += speed;
}
// copy what's left
if (i == block)
rtrig = 1;
if ((ntrig && rtrig) && (i < (range))) {
attr_table.array[(i + dst)] = ((attr_table.array[(i + src)]) * (clear));
i += 1;
}
}
erase = inlet_erase;
if (!erase || !erasegate) {
erasenote = 0;
}
if (inlet_erase) {
overdub = 0;
ertrig = 0;
}
if (!inlet_erase && !ertrig) {
ertrig = 1;
overdub = currentdub;
}
outlet_copy = copyclock;
outlet_copyR = copyclock + RC;
outlet_barcount = length + 1;
outlet_overdub = overdub;
outlet_play = play;
outlet_record = record;
outlet_wait = wait;
outlet_overdub = overdub;
outlet_length = lengthout;
outlet_stepunQR = stepunQ;
outlet_stepunQP = stepunQ + R;
outlet_stepunQCC = stepunQ + R + budd;
outlet_recshift = recshift;
outlet_cleartrigger = ltrig;
outlet_reset = xtrigQ;
outlet_erasenote = erasenote;
outlet_tablesize =
(attr_clipslots * (budd + bendvoice)) + budd + budd + attr_clipslots;
if (dev != MIDI_DEVICE_INTERNAL) {
if ((status == MIDI_NOTE_ON + (attr_channel - 1)) && (data2) && erase) {
erasenote = data1;
erasegate = 1;
MidiSend3((midi_device_t)attr_output, MIDI_NOTE_OFF + (attr_channel - 1),
data1, data2);
}
if (((status == MIDI_NOTE_OFF + (attr_channel - 1)) ||
((status == MIDI_NOTE_ON + (attr_channel - 1)) && (!data2))) &&
erase) {
if (erasenote == data1) {
erasegate = 0;
}
}
}