Allow to send immediate PC messages without closing the dialog.
[ardour.git] / scripts / _midi_lfo.lua
1 ardour {
2         ["type"]    = "dsp",
3         name        = "MIDI LFO",
4         category    = "Example", -- Utility
5         license     = "MIT",
6         author      = "Ardour Lua Task Force",
7         description = [[MIDI CC LFO Example -- Triangle full scale CC Parameter automation]]
8 }
9
10 function dsp_ioconfig ()
11         return { { midi_in = 1, midi_out = 1, audio_in = 0, audio_out = 0}, }
12 end
13
14 function dsp_params ()
15         return
16         {
17                 { ["type"] = "input", name = "BPM", min = 40, max = 200, default = 60, unit="BPM"},
18                 { ["type"] = "input", name = "CC",  min = 0, max = 127,  default = 1, integer = true },
19         }
20 end
21
22 local samplerate
23 local time = 0
24 local step = 0
25
26 function dsp_init (rate)
27         samplerate = rate
28         local bpm = 120
29         spb = rate * 60 / bpm
30 end
31
32 function dsp_run (_, _, n_samples)
33         assert (type(midiin) == "table")
34         assert (type(midiout) == "table")
35
36         local ctrl = CtrlPorts:array ()
37         local bpm = ctrl[1]
38         local cc  = ctrl[2]
39
40         local spb = samplerate * 60 / bpm -- samples per beat
41         local sps = spb / 254 -- samples per step (0..127..1 = 254 steps)
42
43         assert (sps > 1)
44         local i = 1
45         local m = 1
46
47         for ts = 1, n_samples do
48                 time = time + 1
49
50                 -- forward incoming midi
51                 if i <= #midiin then
52                         while midiin[i]["time"] == ts do
53                                 midiout[m] = midiin[i]
54                                 i = i + 1
55                                 m = m + 1
56                                 if i > #midiin then break end
57                         end
58                 end
59
60                 -- inject LFO events
61                 if time >= spb then
62                         local val
63                         if step > 127 then val = 254 - step else val = step end
64
65                         midiout[m] = {}
66                         midiout[m]["time"] = ts
67                         midiout[m]["data"] = { 0xb0, cc, val }
68
69                         m = m + 1
70                         time = time - sps
71                         if step == 253 then step = 0 else step = step + 1 end
72                 end
73         end
74 end