Add a LTC generator to the dummy backend
This commit is contained in:
parent
a3dd948c02
commit
7b7cc9ea6d
@ -33,6 +33,7 @@
|
||||
#include "dummy_midi_seq.h"
|
||||
|
||||
#include "pbd/error.h"
|
||||
#include "pbd/compose.h"
|
||||
#include "ardour/port_manager.h"
|
||||
#include "pbd/i18n.h"
|
||||
|
||||
@ -127,6 +128,7 @@ DummyAudioBackend::enumerate_devices () const
|
||||
_device_status.push_back (DeviceStatus (_("Sine Sweep Swell"), true));
|
||||
_device_status.push_back (DeviceStatus (_("Square Sweep"), true));
|
||||
_device_status.push_back (DeviceStatus (_("Square Sweep Swell"), true));
|
||||
_device_status.push_back (DeviceStatus (_("LTC"), true));
|
||||
_device_status.push_back (DeviceStatus (_("Loopback"), true));
|
||||
}
|
||||
return _device_status;
|
||||
@ -849,6 +851,8 @@ DummyAudioBackend::register_system_ports()
|
||||
gt = DummyAudioPort::SquareSweep;
|
||||
} else if (_device == _("Square Sweep Swell")) {
|
||||
gt = DummyAudioPort::SquareSweepSwell;
|
||||
} else if (_device == _("LTC")) {
|
||||
gt = DummyAudioPort::LTC;
|
||||
} else if (_device == _("Loopback")) {
|
||||
gt = DummyAudioPort::Loopback;
|
||||
} else if (_device == _("Demolition")) {
|
||||
@ -1655,13 +1659,19 @@ DummyAudioPort::DummyAudioPort (DummyAudioBackend &b, const std::string& name, P
|
||||
, _gen_count2 (0)
|
||||
, _pass (false)
|
||||
, _rn1 (0)
|
||||
, _ltc (0)
|
||||
, _ltcbuf (0)
|
||||
{
|
||||
memset (_buffer, 0, sizeof (_buffer));
|
||||
}
|
||||
|
||||
DummyAudioPort::~DummyAudioPort () {
|
||||
free(_wavetable);
|
||||
ltc_encoder_free (_ltc);
|
||||
delete _ltcbuf;
|
||||
_wavetable = 0;
|
||||
_ltc = 0;
|
||||
_ltcbuf = 0;
|
||||
}
|
||||
|
||||
static std::string format_hz (float freq) {
|
||||
@ -1793,6 +1803,44 @@ DummyAudioPort::setup_generator (GeneratorType const g, float const samplerate,
|
||||
}
|
||||
}
|
||||
break;
|
||||
case LTC:
|
||||
switch (c % 4) {
|
||||
case 0:
|
||||
_ltc = ltc_encoder_create (samplerate, 25, LTC_TV_625_50, 0);
|
||||
name = "LTC25";
|
||||
break;
|
||||
case 1:
|
||||
_ltc = ltc_encoder_create (samplerate, 30, LTC_TV_1125_60, 0);
|
||||
name = "LTC30";
|
||||
break;
|
||||
case 2:
|
||||
_ltc = ltc_encoder_create (samplerate, 30001.f / 1001.f, LTC_TV_525_60, 0);
|
||||
name = "LTC29df";
|
||||
break;
|
||||
case 3:
|
||||
_ltc = ltc_encoder_create (samplerate, 24, LTC_TV_FILM_24, 0);
|
||||
name = "LTC30";
|
||||
break;
|
||||
}
|
||||
_ltc_spd = 1.0;
|
||||
_ltc_rand = floor(c / 4) * .001f;
|
||||
if (c < 4) {
|
||||
name += " (locked)";
|
||||
} else {
|
||||
name += " (varspd)";
|
||||
}
|
||||
SMPTETimecode tc;
|
||||
tc.years = 0;
|
||||
tc.months = 0;
|
||||
tc.days = 0;
|
||||
tc.hours = (3 * (c / 4)) % 24; // XXX
|
||||
tc.mins = 0;
|
||||
tc.secs = 0;
|
||||
tc.frame = 0;
|
||||
ltc_encoder_set_timecode (_ltc, &tc);
|
||||
name += string_compose ("@%1h", (int)tc.hours);
|
||||
_ltcbuf = new RingBuffer<Sample> (std::max (DummyAudioBackend::max_buffer_size() * 2.f, samplerate));
|
||||
break;
|
||||
case Loopback:
|
||||
_wavetable = (Sample*) malloc (DummyAudioBackend::max_buffer_size() * sizeof(Sample));
|
||||
break;
|
||||
@ -1996,6 +2044,28 @@ void DummyAudioPort::generate (const pframes_t n_samples)
|
||||
_buffer[i] = _b0 + _b1 + _b2 + white * 0.1848f;
|
||||
}
|
||||
break;
|
||||
case LTC:
|
||||
while (_ltcbuf->read_space () < n_samples) {
|
||||
// we should pre-allocate (or add a zero-copy libltc API), whatever.
|
||||
ltcsnd_sample_t* enc_buf = (ltcsnd_sample_t*) malloc (ltc_encoder_get_buffersize (_ltc) * sizeof (ltcsnd_sample_t));
|
||||
for (int byteCnt = 0; byteCnt < 10; byteCnt++) {
|
||||
if (_ltc_rand != 0.f) {
|
||||
_ltc_spd += randf () * _ltc_rand;
|
||||
_ltc_spd = std::min (1.5f, std::max (0.5f, _ltc_spd));
|
||||
}
|
||||
ltc_encoder_encode_byte (_ltc, byteCnt, _ltc_spd);
|
||||
const int len = ltc_encoder_get_buffer (_ltc, enc_buf);
|
||||
for (int i = 0; i < len; ++i) {
|
||||
const float v1 = enc_buf[i] - 128;
|
||||
Sample v = v1 * 0.002;
|
||||
_ltcbuf->write (&v, 1);
|
||||
}
|
||||
}
|
||||
ltc_encoder_inc_timecode (_ltc);
|
||||
free (enc_buf);
|
||||
}
|
||||
_ltcbuf->read (_buffer, n_samples);
|
||||
break;
|
||||
}
|
||||
_gen_cycle = true;
|
||||
}
|
||||
|
@ -28,9 +28,12 @@
|
||||
#include <stdint.h>
|
||||
#include <pthread.h>
|
||||
|
||||
#include <ltc.h>
|
||||
|
||||
#include <boost/shared_ptr.hpp>
|
||||
|
||||
#include "pbd/natsort.h"
|
||||
#include "pbd/ringbuffer.h"
|
||||
#include "ardour/types.h"
|
||||
#include "ardour/audio_backend.h"
|
||||
#include "ardour/dsp_load_calculator.h"
|
||||
@ -167,6 +170,7 @@ class DummyAudioPort : public DummyPort {
|
||||
SineSweepSwell,
|
||||
SquareSweep,
|
||||
SquareSweepSwell,
|
||||
LTC,
|
||||
Loopback,
|
||||
};
|
||||
std::string setup_generator (GeneratorType const, float const, int, int);
|
||||
@ -194,6 +198,12 @@ class DummyAudioPort : public DummyPort {
|
||||
float grandf ();
|
||||
bool _pass;
|
||||
float _rn1;
|
||||
// LTC generator
|
||||
LTCEncoder* _ltc;
|
||||
RingBuffer<Sample>* _ltcbuf;
|
||||
float _ltc_spd;
|
||||
float _ltc_rand;
|
||||
|
||||
|
||||
}; // class DummyAudioPort
|
||||
|
||||
|
@ -24,7 +24,7 @@ def build(bld):
|
||||
obj.includes = ['.']
|
||||
obj.name = 'dummy_audiobackend'
|
||||
obj.target = 'dummy_audiobackend'
|
||||
obj.use = 'libardour libpbd'
|
||||
obj.use = 'libardour libpbd libltc'
|
||||
obj.uselib = 'GLIBMM XML'
|
||||
obj.install_path = os.path.join(bld.env['LIBDIR'], 'backends')
|
||||
obj.defines = ['PACKAGE="' + I18N_PACKAGE + '"',
|
||||
|
Loading…
Reference in New Issue
Block a user