Vapor: add channel/object-ID map

This commit is contained in:
Robin Gareus 2024-02-23 22:22:50 +01:00
parent c6f8002561
commit 61c6d2bfa1
Signed by: rgareus
GPG Key ID: A090BCE02CF57F04
3 changed files with 58 additions and 34 deletions

View File

@ -97,7 +97,7 @@ public:
samplecnt_t signal_latency () const;
/* XXX this is only for testing */
void set_bed_mix (bool on, std::string const& ref);
void set_bed_mix (bool on, std::string const& ref, int* cmap = NULL);
int set_state (XMLNode const&, int version);
@ -112,6 +112,8 @@ private:
void maybe_send_metadata (size_t id, pframes_t frame, pan_t const v[num_pan_parameters], bool force = false);
void evaluate (size_t id, std::shared_ptr<SurroundPannable> const&, timepos_t const& , pframes_t, bool force = false);
void reset_object_map ();
std::shared_ptr<LV2Plugin> _surround_processor;
LUFSMeter _lufs_meter;
@ -151,7 +153,8 @@ private:
uint8_t _atom_buf[8192];
pan_t _current_value[max_object_id][num_pan_parameters];
int _current_render_mode[max_object_id];
size_t _current_n_objects;
size_t _channel_id_map[max_object_id];
size_t _current_n_channels;
MainOutputFormat _current_output_format;
BufferSet _surround_bufs;
ChanMapping _in_map;

View File

@ -74,7 +74,7 @@ SurroundReturn::SurroundReturn (Session& s, Route* r)
, _au_samples_processed (0)
#endif
, _have_au_renderer (false)
, _current_n_objects (max_object_id)
, _current_n_channels (max_object_id)
, _current_output_format (OUTPUT_FORMAT_7_1_4)
, _in_map (ChanCount (DataType::AUDIO, 128))
, _out_map (ChanCount (DataType::AUDIO, 14 + 6 /* Loudness Meter */))
@ -109,6 +109,7 @@ SurroundReturn::SurroundReturn (Session& s, Route* r)
for (size_t i = 0; i < max_object_id; ++i) {
_current_render_mode[i] = -1;
_channel_id_map[i] = i;
for (size_t p = 0; p < num_pan_parameters; ++p) {
_current_value[i][p] = -1111; /* some invalid data that forces an update */
}
@ -264,15 +265,34 @@ SurroundReturn::flush ()
}
void
SurroundReturn::set_bed_mix (bool on, std::string const& ref)
SurroundReturn::reset_object_map ()
{
for (uint32_t i = 0; i < max_object_id; ++i) {
_channel_id_map[i] = i;
}
}
void
SurroundReturn::set_bed_mix (bool on, std::string const& ref, int* cmap)
{
_with_bed = on;
if (!_with_bed) {
_export_reference.clear ();
reset_object_map ();
return;
}
_export_reference = ref;
if (!cmap) {
reset_object_map ();
} else {
for (uint32_t i = 0; i < max_object_id; ++i) {
if (cmap[i] >= 0 && (size_t) cmap[i] <= max_object_id) {
_channel_id_map[i] = cmap[i];
}
}
}
}
void
@ -295,7 +315,7 @@ SurroundReturn::run (BufferSet& bufs, samplepos_t start_sample, samplepos_t end_
RouteList rl = *_session.get_routes (); // XXX this allocates memory
rl.sort (Stripable::Sorter (true));
size_t id = with_bed ? 0 : 10; // First 10 IDs are reseved for bed mixes
size_t cid = with_bed ? 0 : 10; // First 10 IDs are reseved for bed mixes
for (auto const& r : rl) {
std::shared_ptr<SurroundSend> ss;
@ -309,15 +329,19 @@ SurroundReturn::run (BufferSet& bufs, samplepos_t start_sample, samplepos_t end_
timepos_t unused_start, unused_end;
samplecnt_t latency = effective_latency ();
for (uint32_t s = 0; s < ss->bufs ().count ().n_audio () && id < max_object_id; ++s, ++id) {
for (uint32_t s = 0; s < ss->bufs ().count ().n_audio () && cid < max_object_id; ++s, ++cid) {
std::shared_ptr<SurroundPannable> const& p (ss->pan_param (s, unused_start, unused_end));
AutoState const as = p->automation_state ();
bool const automated = (as & Play) || ((as & (Touch | Latch)) && !p->touching ());
AudioBuffer& dst_ab (_surround_bufs.get_audio (id));
AudioBuffer& dst_ab (_surround_bufs.get_audio (cid));
AudioBuffer const& src_ab (ss->bufs ().get_audio (s));
if (id > 9) {
const uint32_t id = cid;
const uint32_t oid = _channel_id_map[cid];
if (oid > 9) {
/* object */
dst_ab.read_from (src_ab, nframes);
if (!automated || start_sample >= end_sample) {
@ -364,7 +388,7 @@ SurroundReturn::run (BufferSet& bufs, samplepos_t start_sample, samplepos_t end_
dst_ab.merge_from (src_ab, nframes);
}
if (id > 9 || with_bed) {
if (oid > 9 || with_bed) {
/* configure near/mid/far - not sample-accurate */
int const brm = p->binaural_render_mode->get_value ();
if (brm != _current_render_mode[id]) {
@ -378,16 +402,16 @@ SurroundReturn::run (BufferSet& bufs, samplepos_t start_sample, samplepos_t end_
}
if (id >= max_object_id) {
if (cid >= max_object_id) {
break;
}
}
if (_current_n_objects != id) {
_current_n_objects = id;
if (_current_n_channels != cid) {
_current_n_channels = cid;
#if defined(LV2_EXTENDED) && defined(HAVE_LV2_1_10_0)
URIMap::URIDs const& urids = URIMap::instance ().urids;
forge_int_msg (urids.surr_Settings, urids.surr_ChannelCount, _current_n_objects);
forge_int_msg (urids.surr_Settings, urids.surr_ChannelCount, _current_n_channels);
#endif
}
@ -425,7 +449,7 @@ SurroundReturn::run (BufferSet& bufs, samplepos_t start_sample, samplepos_t end_
forge_int_msg (urids.surr_ExportStart, urids.time_frame, meter_offset);
/* Re-transmit pan pos - using export-start */
size_t id = with_bed ? 0 : 10; // First 10 IDs are reseved for bed mixes
size_t cid = with_bed ? 0 : 10; // First 10 IDs are reseved for bed mixes
for (auto const& r : rl) {
std::shared_ptr<SurroundSend> ss;
if (!r->active ()) {
@ -435,12 +459,15 @@ SurroundReturn::run (BufferSet& bufs, samplepos_t start_sample, samplepos_t end_
continue;
}
timepos_t unused_start, unused_end;
for (uint32_t s = 0; s < ss->bufs ().count ().n_audio () && id < max_object_id; ++s, ++id) {
for (uint32_t s = 0; s < ss->bufs ().count ().n_audio () && cid < max_object_id; ++s, ++cid) {
std::shared_ptr<SurroundPannable> const& p (ss->pan_param (s, unused_start, unused_end));
AutoState const as = p->automation_state ();
bool const automated = (as & Play) || ((as & (Touch | Latch)) && !p->touching ());
if (id > 9) {
const uint32_t id = cid;
const uint32_t oid = _channel_id_map[cid];
if (oid > 9) {
if (!automated) {
pan_t const v[num_pan_parameters] = {
(pan_t)p->pan_pos_x->get_value (),
@ -455,7 +482,7 @@ SurroundReturn::run (BufferSet& bufs, samplepos_t start_sample, samplepos_t end_
}
}
}
if (id >= max_object_id) {
if (cid >= max_object_id) {
break;
}
}

View File

@ -24,7 +24,7 @@ function factory () return function ()
end
-- place `Dolby_Atmos_Storage_SIDK_v2.3.2/Tools/linux/lin64_fpic/master_info` in $PATH
os.execute ("master_info -printProgramData -printMetadata \"" .. rv['file'] .. "\" > /tmp/adm.info")
os.execute ("master_info -printMetadata \"" .. rv['file'] .. "\" > /tmp/adm.info")
if Session:get_tracks():size() == 0 then
print ("Importing Files ...")
@ -41,10 +41,8 @@ function factory () return function ()
end
local meta = {}
local chan_type = {[0] = 0, [1] = 1, [2] = 2, [3] = 3, [4] = 6, [5] = 7, [6] = 8, [7] = 9, [8] = 12, [9] = 13}
local chan_beds = {[0] = 0, [1] = 0, [2] = 0, [3] = 0, [4] = 0, [5] = 0, [6] = 0, [7] = 0, [8] = 0, [9] = 0}
local chan_map = {}
local last_chan = 0
local ffoa_sec = 0
for line in io.lines('/tmp/adm.info') do
@ -53,19 +51,9 @@ function factory () return function ()
last_chan = tonumber (chn)
goto next
end
local rv, _, chn = string.find (line, "channel type: (%a+)")
local rv, _, idx = string.find (line, "source channel index: (%d+)")
if rv then
chan_type[last_chan] = chn
goto next
end
local rv, _, bed = string.find (line, "object/bed ID: (%d+)")
if rv then
chan_beds[last_chan] = tonumber(bed)
goto next
end
local rv, _, ffoa = string.find (line, "FFOA: ([%d%.-]+) sec")
if rv then
ffoa_sec = tonumber (ffoa)
chan_map[last_chan] = tonumber(idx)
goto next
end
@ -111,6 +99,12 @@ function factory () return function ()
::skip::
end
Session:surround_master():surround_return():set_bed_mix (true, rv['file'])
local imap = C.IntVector()
for k = 0, 127 do
v = chan_map[k] or k
imap:add ({v})
end
Session:surround_master():surround_return():set_bed_mix (true, rv['file'], imap:to_array ())
print ("OK")
end end