Attempt to fix some confusions caused by bundles containing
different types of port; if we loop over N MIDI channels of a mixed bundle, for example, we must convert 0...N to the indices of the channels within the bundle. Also remove the hack of creating new bundles to contain a subset of another bundle's ports; if you do this, any signals emitted by the other bundle are ignored. Should fix #4454. git-svn-id: svn://localhost/ardour2/branches/3.0@10490 d708f5d6-7413-0410-9779-e7cbd77b26cf
This commit is contained in:
parent
9fa8238d9d
commit
19e97d1d64
|
@ -388,11 +388,10 @@ PortGroupList::gather (ARDOUR::Session* session, ARDOUR::DataType type, bool inp
|
|||
}
|
||||
|
||||
for (list<boost::shared_ptr<IO> >::iterator j = i->ios.begin(); j != i->ios.end(); ++j) {
|
||||
boost::shared_ptr<Bundle> b = bundle_for_type ((*j)->bundle(), type);
|
||||
if (tv) {
|
||||
g->add_bundle (b, *j, tv->color ());
|
||||
g->add_bundle ((*j)->bundle(), *j, tv->color ());
|
||||
} else {
|
||||
g->add_bundle (b, *j);
|
||||
g->add_bundle ((*j)->bundle(), *j);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -405,26 +404,21 @@ PortGroupList::gather (ARDOUR::Session* session, ARDOUR::DataType type, bool inp
|
|||
|
||||
for (BundleList::iterator i = b->begin(); i != b->end(); ++i) {
|
||||
if (boost::dynamic_pointer_cast<UserBundle> (*i) && (*i)->ports_are_inputs() == inputs) {
|
||||
boost::shared_ptr<Bundle> b = bundle_for_type (*i, type);
|
||||
system->add_bundle (b, allow_dups);
|
||||
system->add_bundle (*i, allow_dups);
|
||||
}
|
||||
}
|
||||
|
||||
for (BundleList::iterator i = b->begin(); i != b->end(); ++i) {
|
||||
if (boost::dynamic_pointer_cast<UserBundle> (*i) == 0 && (*i)->ports_are_inputs() == inputs) {
|
||||
boost::shared_ptr<Bundle> b = bundle_for_type (*i, type);
|
||||
system->add_bundle (b, allow_dups);
|
||||
system->add_bundle (*i, allow_dups);
|
||||
}
|
||||
}
|
||||
|
||||
/* Ardour stuff */
|
||||
|
||||
if (!inputs) {
|
||||
boost::shared_ptr<Bundle> b = bundle_for_type (session->the_auditioner()->output()->bundle(), type);
|
||||
ardour->add_bundle (b);
|
||||
|
||||
b = bundle_for_type (session->click_io()->bundle(), type);
|
||||
ardour->add_bundle (b);
|
||||
ardour->add_bundle (session->the_auditioner()->output()->bundle());
|
||||
ardour->add_bundle (session->click_io()->bundle());
|
||||
}
|
||||
|
||||
/* Ardour's surfaces */
|
||||
|
@ -559,16 +553,14 @@ PortGroupList::gather (ARDOUR::Session* session, ARDOUR::DataType type, bool inp
|
|||
for (DataType::iterator i = DataType::begin(); i != DataType::end(); ++i) {
|
||||
if (!extra_system[*i].empty()) {
|
||||
boost::shared_ptr<Bundle> b = make_bundle_from_ports (extra_system[*i], *i, inputs);
|
||||
boost::shared_ptr<Bundle> bt = bundle_for_type (b, type);
|
||||
system->add_bundle (bt);
|
||||
system->add_bundle (b);
|
||||
}
|
||||
}
|
||||
|
||||
for (DataType::iterator i = DataType::begin(); i != DataType::end(); ++i) {
|
||||
if (!extra_other[*i].empty()) {
|
||||
boost::shared_ptr<Bundle> b = make_bundle_from_ports (extra_other[*i], *i, inputs);
|
||||
boost::shared_ptr<Bundle> bt = bundle_for_type (b, type);
|
||||
other->add_bundle (bt);
|
||||
other->add_bundle (b);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -780,30 +772,3 @@ PortGroupList::empty () const
|
|||
return _groups.empty ();
|
||||
}
|
||||
|
||||
/** Take a bundle, and either return it, if it contains only ports of type \a t,
|
||||
* or return a new bundle with those ports from \a b which are of type \a t.
|
||||
* Note that t == NIL is taken to mean "all types".
|
||||
*/
|
||||
boost::shared_ptr<Bundle>
|
||||
PortGroupList::bundle_for_type (boost::shared_ptr<Bundle> b, DataType t) const
|
||||
{
|
||||
/* We are asked for a bundle with all types, so that's easy */
|
||||
if (t == DataType::NIL) {
|
||||
return b;
|
||||
}
|
||||
|
||||
if (b->nchannels().get(t) == b->nchannels().n_total()) {
|
||||
/* All channels on b are of the correct type, so just return b */
|
||||
return b;
|
||||
}
|
||||
|
||||
/* We must build a new bundle */
|
||||
boost::shared_ptr<Bundle> n (new ARDOUR::Bundle (b->name(), b->ports_are_inputs()));
|
||||
for (uint32_t i = 0; i < b->nchannels().n_total(); ++i) {
|
||||
if (b->channel_type(i) == t) {
|
||||
n->add_channel (b->channel_name (i), t, b->channel_ports (i));
|
||||
}
|
||||
}
|
||||
|
||||
return n;
|
||||
}
|
||||
|
|
|
@ -146,7 +146,6 @@ class PortGroupList : public sigc::trackable
|
|||
void maybe_add_processor_to_list (
|
||||
boost::weak_ptr<ARDOUR::Processor>, std::list<boost::shared_ptr<ARDOUR::IO> > *, bool, std::set<boost::shared_ptr<ARDOUR::IO> > &
|
||||
);
|
||||
boost::shared_ptr<ARDOUR::Bundle> bundle_for_type (boost::shared_ptr<ARDOUR::Bundle>, ARDOUR::DataType) const;
|
||||
|
||||
mutable PortGroup::BundleList _bundles;
|
||||
List _groups;
|
||||
|
|
|
@ -156,7 +156,11 @@ PortMatrixColumnLabels::render (cairo_t* cr)
|
|||
|
||||
for (uint32_t j = 0; j < C; ++j) {
|
||||
Gdk::Color c = (*i)->has_colour ? (*i)->colour : get_a_bundle_colour (N);
|
||||
render_channel_name (cr, background_colour (), c, x, 0, ARDOUR::BundleChannel ((*i)->bundle, j));
|
||||
ARDOUR::BundleChannel bc (
|
||||
(*i)->bundle,
|
||||
(*i)->bundle->type_channel_to_overall (_matrix->type (), j)
|
||||
);
|
||||
render_channel_name (cr, background_colour (), c, x, 0, bc);
|
||||
x += grid_spacing();
|
||||
}
|
||||
|
||||
|
@ -487,9 +491,11 @@ PortMatrixColumnLabels::motion (double x, double y)
|
|||
|
||||
list<PortMatrixNode> n;
|
||||
|
||||
uint32_t const N = _matrix->count_of_our_type (w.bundle->nchannels ());
|
||||
|
||||
for (uint32_t i = 0; i < N; ++i) {
|
||||
for (uint32_t i = 0; i < w.bundle->nchannels().n_total(); ++i) {
|
||||
if (!_matrix->should_show (w.bundle->channel_type (i))) {
|
||||
continue;
|
||||
}
|
||||
|
||||
ARDOUR::BundleChannel const bc (w.bundle, i);
|
||||
n.push_back (PortMatrixNode (ARDOUR::BundleChannel (), bc));
|
||||
}
|
||||
|
|
|
@ -197,7 +197,7 @@ PortMatrixComponent::position_to_channel (double p, double, boost::shared_ptr<co
|
|||
|
||||
uint32_t const s = _matrix->count_of_our_type_min_1 ((*j)->bundle->nchannels());
|
||||
if (p < s) {
|
||||
return ARDOUR::BundleChannel ((*j)->bundle, p);
|
||||
return ARDOUR::BundleChannel ((*j)->bundle, (*j)->bundle->type_channel_to_overall (_matrix->type (), p));
|
||||
} else {
|
||||
p -= s;
|
||||
}
|
||||
|
|
|
@ -191,8 +191,16 @@ PortMatrixGrid::render (cairo_t* cr)
|
|||
for (uint32_t l = 0; l < _matrix->count_of_our_type ((*j)->bundle->nchannels()); ++l) {
|
||||
|
||||
ARDOUR::BundleChannel c[2];
|
||||
c[_matrix->column_index()] = ARDOUR::BundleChannel ((*i)->bundle, k);
|
||||
c[_matrix->row_index()] = ARDOUR::BundleChannel ((*j)->bundle, l);
|
||||
|
||||
c[_matrix->column_index()] = ARDOUR::BundleChannel (
|
||||
(*i)->bundle,
|
||||
(*i)->bundle->type_channel_to_overall (_matrix->type (), k)
|
||||
);
|
||||
|
||||
c[_matrix->row_index()] = ARDOUR::BundleChannel (
|
||||
(*j)->bundle,
|
||||
(*j)->bundle->type_channel_to_overall (_matrix->type (), l)
|
||||
);
|
||||
|
||||
if (c[0].bundle->channel_type (c[0].channel) != c[1].bundle->channel_type (c[1].channel)) {
|
||||
/* these two channels are of different types */
|
||||
|
@ -328,13 +336,6 @@ PortMatrixGrid::button_press (double x, double y, int b, uint32_t t, guint)
|
|||
void
|
||||
PortMatrixGrid::set_association (PortMatrixNode node, bool s)
|
||||
{
|
||||
if (node.row.bundle->nchannels().n_total() == 0 || node.column.bundle->nchannels().n_total() == 0) {
|
||||
/* One of the bundles has no channels, which means that it has none of the appropriate type,
|
||||
and is only being displayed to look pretty. So we don't need to do anything.
|
||||
*/
|
||||
return;
|
||||
}
|
||||
|
||||
if (_matrix->show_only_bundles()) {
|
||||
|
||||
for (uint32_t i = 0; i < node.column.bundle->nchannels().n_total(); ++i) {
|
||||
|
@ -358,6 +359,7 @@ PortMatrixGrid::set_association (PortMatrixNode node, bool s)
|
|||
ARDOUR::BundleChannel c[2];
|
||||
c[_matrix->row_index()] = node.row;
|
||||
c[_matrix->column_index()] = node.column;
|
||||
|
||||
_matrix->set_state (c, s);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -117,7 +117,12 @@ PortMatrixRowLabels::render (cairo_t* cr)
|
|||
uint32_t const N = _matrix->count_of_our_type ((*i)->bundle->nchannels());
|
||||
for (uint32_t j = 0; j < N; ++j) {
|
||||
Gdk::Color c = (*i)->has_colour ? (*i)->colour : get_a_bundle_colour (M);
|
||||
render_channel_name (cr, background_colour (), c, 0, y, ARDOUR::BundleChannel ((*i)->bundle, j));
|
||||
ARDOUR::BundleChannel bc (
|
||||
(*i)->bundle,
|
||||
(*i)->bundle->type_channel_to_overall (_matrix->type (), j)
|
||||
);
|
||||
|
||||
render_channel_name (cr, background_colour (), c, 0, y, bc);
|
||||
y += grid_spacing();
|
||||
++M;
|
||||
}
|
||||
|
@ -334,8 +339,7 @@ PortMatrixRowLabels::motion (double x, double y)
|
|||
list<PortMatrixNode> n;
|
||||
|
||||
for (uint32_t i = 0; i < w.bundle->nchannels().n_total(); ++i) {
|
||||
|
||||
if (!_matrix->should_show (w.bundle->channel_type(i))) {
|
||||
if (!_matrix->should_show (w.bundle->channel_type (i))) {
|
||||
continue;
|
||||
}
|
||||
|
||||
|
|
|
@ -100,6 +100,7 @@ class Bundle : public PBD::ScopedConnectionList
|
|||
void disconnect (boost::shared_ptr<Bundle>, AudioEngine &);
|
||||
bool connected_to (boost::shared_ptr<Bundle>, AudioEngine &);
|
||||
bool has_same_ports (boost::shared_ptr<Bundle>) const;
|
||||
uint32_t type_channel_to_overall (DataType, uint32_t) const;
|
||||
|
||||
void set_name (std::string const &);
|
||||
|
||||
|
|
|
@ -517,3 +517,44 @@ Bundle::operator== (Bundle const & other)
|
|||
{
|
||||
return _channel == other._channel;
|
||||
}
|
||||
|
||||
/** Given an index of a channel as the nth channel of a particular type,
|
||||
* return an index of that channel when considering channels of all types.
|
||||
*
|
||||
* e.g. given a bundle with channels:
|
||||
* fred [audio]
|
||||
* jim [audio]
|
||||
* sheila [midi]
|
||||
*
|
||||
* If t == MIDI and c == 0, then we would return 2, as 2 is the index of the
|
||||
* 0th MIDI channel.
|
||||
*/
|
||||
|
||||
uint32_t
|
||||
Bundle::type_channel_to_overall (DataType t, uint32_t c) const
|
||||
{
|
||||
Glib::Mutex::Lock lm (_channel_mutex);
|
||||
|
||||
vector<Channel>::const_iterator i = _channel.begin ();
|
||||
|
||||
uint32_t o = 0;
|
||||
|
||||
while (1) {
|
||||
|
||||
assert (i != _channel.end ());
|
||||
|
||||
if (i->type != t) {
|
||||
++i;
|
||||
} else {
|
||||
if (c == 0) {
|
||||
return o;
|
||||
}
|
||||
--c;
|
||||
}
|
||||
|
||||
++o;
|
||||
}
|
||||
|
||||
/* NOTREACHED */
|
||||
return -1;
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue