mirror of
https://github.com/Ardour/ardour.git
synced 2025-12-17 12:16:30 +01:00
More port matrix re-working. Global matrix now has separate visibility buttons
for ins and outs. The matrix will now be arranged so that more ports are labelled horizontally than vertically, to aid readability. git-svn-id: svn://localhost/ardour2/branches/3.0@4467 d708f5d6-7413-0410-9779-e7cbd77b26cf
This commit is contained in:
parent
24aab941eb
commit
a384dab130
23 changed files with 843 additions and 726 deletions
|
|
@ -33,49 +33,40 @@
|
|||
BundleEditorMatrix::BundleEditorMatrix (
|
||||
ARDOUR::Session& session, boost::shared_ptr<ARDOUR::Bundle> bundle
|
||||
)
|
||||
: PortMatrix (session, bundle->type(), bundle->ports_are_inputs())
|
||||
: PortMatrix (session, bundle->type()),
|
||||
_bundle (bundle)
|
||||
{
|
||||
_port_group = new PortGroup ("", true);
|
||||
_port_group = boost::shared_ptr<PortGroup> (new PortGroup (""));
|
||||
_port_group->add_bundle (bundle);
|
||||
_row_ports.push_back (_port_group);
|
||||
}
|
||||
|
||||
BundleEditorMatrix::~BundleEditorMatrix ()
|
||||
{
|
||||
delete _port_group;
|
||||
_ports[OURS].add_group (_port_group);
|
||||
}
|
||||
|
||||
void
|
||||
BundleEditorMatrix::set_state (
|
||||
boost::shared_ptr<ARDOUR::Bundle> ab,
|
||||
uint32_t ac,
|
||||
boost::shared_ptr<ARDOUR::Bundle> bb,
|
||||
uint32_t bc,
|
||||
bool s,
|
||||
uint32_t k
|
||||
)
|
||||
BundleEditorMatrix::setup ()
|
||||
{
|
||||
ARDOUR::Bundle::PortList const& pl = bb->channel_ports (bc);
|
||||
_ports[OTHER].gather (_session, _bundle->ports_are_inputs());
|
||||
PortMatrix::setup ();
|
||||
}
|
||||
|
||||
void
|
||||
BundleEditorMatrix::set_state (ARDOUR::BundleChannel c[2], bool s)
|
||||
{
|
||||
ARDOUR::Bundle::PortList const& pl = c[OTHER].bundle->channel_ports (c[OTHER].channel);
|
||||
for (ARDOUR::Bundle::PortList::const_iterator i = pl.begin(); i != pl.end(); ++i) {
|
||||
if (s) {
|
||||
ab->add_port_to_channel (ac, *i);
|
||||
c[OURS].bundle->add_port_to_channel (c[OURS].channel, *i);
|
||||
} else {
|
||||
ab->remove_port_from_channel (ac, *i);
|
||||
c[OURS].bundle->remove_port_from_channel (c[OURS].channel, *i);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
PortMatrix::State
|
||||
BundleEditorMatrix::get_state (
|
||||
boost::shared_ptr<ARDOUR::Bundle> ab,
|
||||
uint32_t ac,
|
||||
boost::shared_ptr<ARDOUR::Bundle> bb,
|
||||
uint32_t bc
|
||||
) const
|
||||
BundleEditorMatrix::get_state (ARDOUR::BundleChannel c[2]) const
|
||||
{
|
||||
ARDOUR::Bundle::PortList const& pl = bb->channel_ports (bc);
|
||||
ARDOUR::Bundle::PortList const& pl = c[OTHER].bundle->channel_ports (c[OTHER].channel);
|
||||
for (ARDOUR::Bundle::PortList::const_iterator i = pl.begin(); i != pl.end(); ++i) {
|
||||
if (!ab->port_attached_to_channel (ac, *i)) {
|
||||
if (!c[OURS].bundle->port_attached_to_channel (c[OURS].channel, *i)) {
|
||||
return NOT_ASSOCIATED;
|
||||
}
|
||||
}
|
||||
|
|
@ -93,28 +84,28 @@ BundleEditorMatrix::add_channel (boost::shared_ptr<ARDOUR::Bundle> b)
|
|||
return;
|
||||
}
|
||||
|
||||
_port_group->only_bundle()->add_channel (d.get_name());
|
||||
_bundle->add_channel (d.get_name());
|
||||
setup ();
|
||||
}
|
||||
|
||||
void
|
||||
BundleEditorMatrix::remove_channel (boost::shared_ptr<ARDOUR::Bundle> b, uint32_t c)
|
||||
BundleEditorMatrix::remove_channel (ARDOUR::BundleChannel bc)
|
||||
{
|
||||
_port_group->only_bundle()->remove_channel (c);
|
||||
bc.bundle->remove_channel (bc.channel);
|
||||
setup ();
|
||||
}
|
||||
|
||||
void
|
||||
BundleEditorMatrix::rename_channel (boost::shared_ptr<ARDOUR::Bundle> b, uint32_t c)
|
||||
BundleEditorMatrix::rename_channel (ARDOUR::BundleChannel bc)
|
||||
{
|
||||
NameChannelDialog d (b, c);
|
||||
NameChannelDialog d (bc.bundle, bc.channel);
|
||||
d.set_position (Gtk::WIN_POS_MOUSE);
|
||||
|
||||
if (d.run () != Gtk::RESPONSE_ACCEPT) {
|
||||
return;
|
||||
}
|
||||
|
||||
b->set_channel_name (c, d.get_name ());
|
||||
bc.bundle->set_channel_name (bc.channel, d.get_name ());
|
||||
}
|
||||
|
||||
BundleEditor::BundleEditor (ARDOUR::Session& session, boost::shared_ptr<ARDOUR::UserBundle> bundle, bool add)
|
||||
|
|
@ -203,11 +194,11 @@ BundleEditor::input_or_output_changed ()
|
|||
{
|
||||
if (_input_or_output.get_active_text() == _("Output")) {
|
||||
_bundle->set_ports_are_inputs ();
|
||||
_matrix.set_offer_inputs (true);
|
||||
} else {
|
||||
_bundle->set_ports_are_outputs ();
|
||||
_matrix.set_offer_inputs (false);
|
||||
}
|
||||
|
||||
_matrix.setup ();
|
||||
}
|
||||
|
||||
void
|
||||
|
|
|
|||
|
|
@ -35,33 +35,28 @@ class BundleEditorMatrix : public PortMatrix
|
|||
{
|
||||
public:
|
||||
BundleEditorMatrix (ARDOUR::Session &, boost::shared_ptr<ARDOUR::Bundle>);
|
||||
~BundleEditorMatrix ();
|
||||
|
||||
void set_state (
|
||||
boost::shared_ptr<ARDOUR::Bundle> ab,
|
||||
uint32_t ac,
|
||||
boost::shared_ptr<ARDOUR::Bundle> bb,
|
||||
uint32_t bc,
|
||||
bool s,
|
||||
uint32_t k
|
||||
);
|
||||
|
||||
State get_state (
|
||||
boost::shared_ptr<ARDOUR::Bundle> ab,
|
||||
uint32_t ac,
|
||||
boost::shared_ptr<ARDOUR::Bundle> bb,
|
||||
uint32_t bc
|
||||
) const;
|
||||
|
||||
void set_state (ARDOUR::BundleChannel c[2], bool s);
|
||||
State get_state (ARDOUR::BundleChannel c[2]) const;
|
||||
void add_channel (boost::shared_ptr<ARDOUR::Bundle>);
|
||||
void remove_channel (boost::shared_ptr<ARDOUR::Bundle>, uint32_t);
|
||||
bool can_rename_channels () const {
|
||||
return true;
|
||||
bool can_remove_channels (int d) const {
|
||||
return d == OURS;
|
||||
}
|
||||
void rename_channel (boost::shared_ptr<ARDOUR::Bundle>, uint32_t);
|
||||
void remove_channel (ARDOUR::BundleChannel);
|
||||
bool can_rename_channels (int d) const {
|
||||
return d == OURS;
|
||||
}
|
||||
void rename_channel (ARDOUR::BundleChannel);
|
||||
void setup ();
|
||||
|
||||
private:
|
||||
PortGroup* _port_group;
|
||||
enum {
|
||||
OTHER = 0,
|
||||
OURS = 1
|
||||
};
|
||||
|
||||
boost::shared_ptr<PortGroup> _port_group;
|
||||
boost::shared_ptr<ARDOUR::Bundle> _bundle;
|
||||
};
|
||||
|
||||
class BundleEditor : public ArdourDialog
|
||||
|
|
|
|||
|
|
@ -25,45 +25,28 @@
|
|||
#include "ardour/port.h"
|
||||
|
||||
GlobalPortMatrix::GlobalPortMatrix (ARDOUR::Session& s, ARDOUR::DataType t)
|
||||
: PortMatrix (s, t, true),
|
||||
_session (s),
|
||||
_our_port_group_list (t, false)
|
||||
: PortMatrix (s, t)
|
||||
{
|
||||
setup ();
|
||||
|
||||
_column_ports.VisibilityChanged.connect (sigc::mem_fun (*this, &GlobalPortMatrix::group_visibility_changed));
|
||||
}
|
||||
|
||||
void
|
||||
GlobalPortMatrix::group_visibility_changed ()
|
||||
{
|
||||
_row_ports.take_visibility_from (_column_ports);
|
||||
setup ();
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
GlobalPortMatrix::setup ()
|
||||
{
|
||||
_row_ports.gather (_session);
|
||||
_ports[IN].gather (_session, true);
|
||||
_ports[OUT].gather (_session, false);
|
||||
|
||||
PortMatrix::setup ();
|
||||
}
|
||||
|
||||
void
|
||||
GlobalPortMatrix::set_state (
|
||||
boost::shared_ptr<ARDOUR::Bundle> ab,
|
||||
uint32_t ac,
|
||||
boost::shared_ptr<ARDOUR::Bundle> bb,
|
||||
uint32_t bc,
|
||||
bool s,
|
||||
uint32_t k
|
||||
)
|
||||
GlobalPortMatrix::set_state (ARDOUR::BundleChannel c[2], bool s)
|
||||
{
|
||||
ARDOUR::Bundle::PortList const& our_ports = ab->channel_ports (ac);
|
||||
ARDOUR::Bundle::PortList const& other_ports = bb->channel_ports (bc);
|
||||
ARDOUR::Bundle::PortList const & in_ports = c[IN].bundle->channel_ports (c[IN].channel);
|
||||
ARDOUR::Bundle::PortList const & out_ports = c[OUT].bundle->channel_ports (c[OUT].channel);
|
||||
|
||||
for (ARDOUR::Bundle::PortList::const_iterator i = our_ports.begin(); i != our_ports.end(); ++i) {
|
||||
for (ARDOUR::Bundle::PortList::const_iterator j = other_ports.begin(); j != other_ports.end(); ++j) {
|
||||
for (ARDOUR::Bundle::PortList::const_iterator i = in_ports.begin(); i != in_ports.end(); ++i) {
|
||||
for (ARDOUR::Bundle::PortList::const_iterator j = out_ports.begin(); j != out_ports.end(); ++j) {
|
||||
|
||||
ARDOUR::Port* p = _session.engine().get_port_by_name (*i);
|
||||
ARDOUR::Port* q = _session.engine().get_port_by_name (*j);
|
||||
|
|
@ -78,7 +61,7 @@ GlobalPortMatrix::set_state (
|
|||
if (s) {
|
||||
q->connect (*i);
|
||||
} else {
|
||||
q->disconnect (*j);
|
||||
q->disconnect (*i);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -89,18 +72,13 @@ GlobalPortMatrix::set_state (
|
|||
|
||||
|
||||
PortMatrix::State
|
||||
GlobalPortMatrix::get_state (
|
||||
boost::shared_ptr<ARDOUR::Bundle> ab,
|
||||
uint32_t ac,
|
||||
boost::shared_ptr<ARDOUR::Bundle> bb,
|
||||
uint32_t bc
|
||||
) const
|
||||
GlobalPortMatrix::get_state (ARDOUR::BundleChannel c[2]) const
|
||||
{
|
||||
ARDOUR::Bundle::PortList const& our_ports = ab->channel_ports (ac);
|
||||
ARDOUR::Bundle::PortList const& other_ports = bb->channel_ports (bc);
|
||||
ARDOUR::Bundle::PortList const & in_ports = c[IN].bundle->channel_ports (c[IN].channel);
|
||||
ARDOUR::Bundle::PortList const & out_ports = c[OUT].bundle->channel_ports (c[OUT].channel);
|
||||
|
||||
for (ARDOUR::Bundle::PortList::const_iterator i = our_ports.begin(); i != our_ports.end(); ++i) {
|
||||
for (ARDOUR::Bundle::PortList::const_iterator j = other_ports.begin(); j != other_ports.end(); ++j) {
|
||||
for (ARDOUR::Bundle::PortList::const_iterator i = in_ports.begin(); i != in_ports.end(); ++i) {
|
||||
for (ARDOUR::Bundle::PortList::const_iterator j = out_ports.begin(); j != out_ports.end(); ++j) {
|
||||
|
||||
ARDOUR::Port* p = _session.engine().get_port_by_name (*i);
|
||||
ARDOUR::Port* q = _session.engine().get_port_by_name (*j);
|
||||
|
|
|
|||
|
|
@ -31,34 +31,24 @@ public:
|
|||
|
||||
void setup ();
|
||||
|
||||
void set_state (
|
||||
boost::shared_ptr<ARDOUR::Bundle>,
|
||||
uint32_t,
|
||||
boost::shared_ptr<ARDOUR::Bundle>,
|
||||
uint32_t,
|
||||
bool,
|
||||
uint32_t
|
||||
);
|
||||
|
||||
State get_state (
|
||||
boost::shared_ptr<ARDOUR::Bundle>,
|
||||
uint32_t,
|
||||
boost::shared_ptr<ARDOUR::Bundle>,
|
||||
uint32_t
|
||||
) const;
|
||||
void set_state (ARDOUR::BundleChannel c[2], bool);
|
||||
State get_state (ARDOUR::BundleChannel c[2]) const;
|
||||
|
||||
void add_channel (boost::shared_ptr<ARDOUR::Bundle>) {}
|
||||
void remove_channel (boost::shared_ptr<ARDOUR::Bundle>, uint32_t) {}
|
||||
bool can_rename_channels () const {
|
||||
bool can_remove_channels (int d) const {
|
||||
return false;
|
||||
}
|
||||
void remove_channel (ARDOUR::BundleChannel) {}
|
||||
bool can_rename_channels (int d) const {
|
||||
return false;
|
||||
}
|
||||
|
||||
private:
|
||||
void group_visibility_changed ();
|
||||
|
||||
ARDOUR::Session& _session;
|
||||
PortGroupList _our_port_group_list;
|
||||
|
||||
/* see PortMatrix: signal flow from 0 to 1 (out to in) */
|
||||
enum {
|
||||
OUT = 0,
|
||||
IN = 1,
|
||||
};
|
||||
};
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -41,33 +41,39 @@
|
|||
using namespace ARDOUR;
|
||||
using namespace Gtk;
|
||||
|
||||
IOSelector::IOSelector (ARDOUR::Session& session, boost::shared_ptr<ARDOUR::IO> io, bool offer_inputs)
|
||||
: PortMatrix (session, io->default_type(), offer_inputs)
|
||||
, _session (session)
|
||||
IOSelector::IOSelector (ARDOUR::Session& session, boost::shared_ptr<ARDOUR::IO> io, bool in)
|
||||
: PortMatrix (session, io->default_type())
|
||||
, _io (io)
|
||||
, _find_inputs_for_io_outputs (in)
|
||||
{
|
||||
/* Listen for ports changing on the IO */
|
||||
_io->PortCountChanged.connect (sigc::hide (mem_fun (*this, &IOSelector::ports_changed)));
|
||||
|
||||
_port_group = new PortGroup ("", true);
|
||||
_row_ports.push_back (_port_group);
|
||||
/* signal flow from 0 to 1 */
|
||||
if (_find_inputs_for_io_outputs) {
|
||||
_other = 1;
|
||||
_ours = 0;
|
||||
} else {
|
||||
_other = 0;
|
||||
_ours = 1;
|
||||
}
|
||||
|
||||
_port_group = boost::shared_ptr<PortGroup> (new PortGroup (""));
|
||||
_ports[_ours].add_group (_port_group);
|
||||
|
||||
setup ();
|
||||
}
|
||||
|
||||
IOSelector::~IOSelector ()
|
||||
{
|
||||
delete _port_group;
|
||||
}
|
||||
|
||||
void
|
||||
IOSelector::setup ()
|
||||
{
|
||||
_ports[_other].gather (_session, _find_inputs_for_io_outputs);
|
||||
|
||||
_port_group->clear ();
|
||||
_port_group->add_bundle (boost::shared_ptr<ARDOUR::Bundle> (new ARDOUR::Bundle));
|
||||
_port_group->only_bundle()->set_name (_io->name());
|
||||
|
||||
if (offering_input ()) {
|
||||
if (_find_inputs_for_io_outputs) {
|
||||
const PortSet& ps (_io->outputs());
|
||||
|
||||
int j = 0;
|
||||
|
|
@ -106,17 +112,10 @@ IOSelector::ports_changed ()
|
|||
}
|
||||
|
||||
void
|
||||
IOSelector::set_state (
|
||||
boost::shared_ptr<ARDOUR::Bundle> ab,
|
||||
uint32_t ac,
|
||||
boost::shared_ptr<ARDOUR::Bundle> bb,
|
||||
uint32_t bc,
|
||||
bool s,
|
||||
uint32_t k
|
||||
)
|
||||
IOSelector::set_state (ARDOUR::BundleChannel c[2], bool s)
|
||||
{
|
||||
ARDOUR::Bundle::PortList const& our_ports = ab->channel_ports (ac);
|
||||
ARDOUR::Bundle::PortList const& other_ports = bb->channel_ports (bc);
|
||||
ARDOUR::Bundle::PortList const & our_ports = c[_ours].bundle->channel_ports (c[_ours].channel);
|
||||
ARDOUR::Bundle::PortList const & other_ports = c[_other].bundle->channel_ports (c[_other].channel);
|
||||
|
||||
for (ARDOUR::Bundle::PortList::const_iterator i = our_ports.begin(); i != our_ports.end(); ++i) {
|
||||
for (ARDOUR::Bundle::PortList::const_iterator j = other_ports.begin(); j != other_ports.end(); ++j) {
|
||||
|
|
@ -127,13 +126,13 @@ IOSelector::set_state (
|
|||
}
|
||||
|
||||
if (s) {
|
||||
if (!offering_input()) {
|
||||
if (!_find_inputs_for_io_outputs) {
|
||||
_io->connect_input (f, *j, 0);
|
||||
} else {
|
||||
_io->connect_output (f, *j, 0);
|
||||
}
|
||||
} else {
|
||||
if (!offering_input()) {
|
||||
if (!_find_inputs_for_io_outputs) {
|
||||
_io->disconnect_input (f, *j, 0);
|
||||
} else {
|
||||
_io->disconnect_output (f, *j, 0);
|
||||
|
|
@ -144,15 +143,10 @@ IOSelector::set_state (
|
|||
}
|
||||
|
||||
PortMatrix::State
|
||||
IOSelector::get_state (
|
||||
boost::shared_ptr<ARDOUR::Bundle> ab,
|
||||
uint32_t ac,
|
||||
boost::shared_ptr<ARDOUR::Bundle> bb,
|
||||
uint32_t bc
|
||||
) const
|
||||
IOSelector::get_state (ARDOUR::BundleChannel c[2]) const
|
||||
{
|
||||
ARDOUR::Bundle::PortList const& our_ports = ab->channel_ports (ac);
|
||||
ARDOUR::Bundle::PortList const& other_ports = bb->channel_ports (bc);
|
||||
ARDOUR::Bundle::PortList const & our_ports = c[_ours].bundle->channel_ports (c[_ours].channel);
|
||||
ARDOUR::Bundle::PortList const & other_ports = c[_other].bundle->channel_ports (c[_other].channel);
|
||||
|
||||
for (ARDOUR::Bundle::PortList::const_iterator i = our_ports.begin(); i != our_ports.end(); ++i) {
|
||||
for (ARDOUR::Bundle::PortList::const_iterator j = other_ports.begin(); j != other_ports.end(); ++j) {
|
||||
|
|
@ -174,9 +168,9 @@ IOSelector::get_state (
|
|||
}
|
||||
|
||||
uint32_t
|
||||
IOSelector::n_rows () const
|
||||
IOSelector::n_io_ports () const
|
||||
{
|
||||
if (!offering_input()) {
|
||||
if (!_find_inputs_for_io_outputs) {
|
||||
return _io->inputs().num_ports (_io->default_type());
|
||||
} else {
|
||||
return _io->outputs().num_ports (_io->default_type());
|
||||
|
|
@ -184,9 +178,9 @@ IOSelector::n_rows () const
|
|||
}
|
||||
|
||||
uint32_t
|
||||
IOSelector::maximum_rows () const
|
||||
IOSelector::maximum_io_ports () const
|
||||
{
|
||||
if (!offering_input()) {
|
||||
if (!_find_inputs_for_io_outputs) {
|
||||
return _io->input_maximum ().get (_io->default_type());
|
||||
} else {
|
||||
return _io->output_maximum ().get (_io->default_type());
|
||||
|
|
@ -195,9 +189,9 @@ IOSelector::maximum_rows () const
|
|||
|
||||
|
||||
uint32_t
|
||||
IOSelector::minimum_rows () const
|
||||
IOSelector::minimum_io_ports () const
|
||||
{
|
||||
if (!offering_input()) {
|
||||
if (!_find_inputs_for_io_outputs) {
|
||||
return _io->input_minimum ().get (_io->default_type());
|
||||
} else {
|
||||
return _io->output_minimum ().get (_io->default_type());
|
||||
|
|
@ -212,7 +206,7 @@ IOSelector::add_channel (boost::shared_ptr<ARDOUR::Bundle> b)
|
|||
// The IO selector only works for single typed IOs
|
||||
const ARDOUR::DataType t = _io->default_type ();
|
||||
|
||||
if (!offering_input()) {
|
||||
if (!_find_inputs_for_io_outputs) {
|
||||
|
||||
try {
|
||||
_io->add_input_port ("", this);
|
||||
|
|
@ -237,14 +231,14 @@ IOSelector::add_channel (boost::shared_ptr<ARDOUR::Bundle> b)
|
|||
}
|
||||
|
||||
void
|
||||
IOSelector::remove_channel (boost::shared_ptr<ARDOUR::Bundle> b, uint32_t c)
|
||||
IOSelector::remove_channel (ARDOUR::BundleChannel bc)
|
||||
{
|
||||
Port* f = _session.engine().get_port_by_name (b->channel_ports(c)[0]);
|
||||
Port* f = _session.engine().get_port_by_name (bc.bundle->channel_ports(bc.channel)[0]);
|
||||
if (!f) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (offering_input()) {
|
||||
if (_find_inputs_for_io_outputs) {
|
||||
_io->remove_output_port (f, this);
|
||||
} else {
|
||||
_io->remove_input_port (f, this);
|
||||
|
|
@ -273,7 +267,7 @@ IOSelectorWindow::IOSelectorWindow (ARDOUR::Session& session, boost::shared_ptr<
|
|||
get_action_area()->pack_start (disconnect_button, false, false);
|
||||
|
||||
/* Add Port button */
|
||||
if (_selector.maximum_rows() > _selector.n_rows()) {
|
||||
if (_selector.maximum_io_ports() > _selector.n_io_ports()) {
|
||||
add_button.set_name ("IOSelectorButton");
|
||||
add_button.set_image (*Gtk::manage (new Gtk::Image (Gtk::Stock::ADD, Gtk::ICON_SIZE_BUTTON)));
|
||||
get_action_area()->pack_start (add_button, false, false);
|
||||
|
|
@ -323,7 +317,7 @@ IOSelectorWindow::IOSelectorWindow (ARDOUR::Session& session, boost::shared_ptr<
|
|||
void
|
||||
IOSelectorWindow::ports_changed ()
|
||||
{
|
||||
if (_selector.maximum_rows() > _selector.n_rows()) {
|
||||
if (_selector.maximum_io_ports() > _selector.n_io_ports()) {
|
||||
add_button.set_sensitive (true);
|
||||
} else {
|
||||
add_button.set_sensitive (false);
|
||||
|
|
@ -358,7 +352,7 @@ IOSelectorWindow::io_name_changed (void* src)
|
|||
|
||||
string title;
|
||||
|
||||
if (!_selector.offering_input()) {
|
||||
if (!_selector.find_inputs_for_io_outputs()) {
|
||||
title = string_compose(_("%1 input"), _selector.io()->name());
|
||||
} else {
|
||||
title = string_compose(_("%1 output"), _selector.io()->name());
|
||||
|
|
|
|||
|
|
@ -27,43 +27,41 @@ namespace ARDOUR {
|
|||
class PortInsert;
|
||||
}
|
||||
|
||||
class IOSelector : public PortMatrix {
|
||||
class IOSelector : public PortMatrix
|
||||
{
|
||||
public:
|
||||
IOSelector (ARDOUR::Session&, boost::shared_ptr<ARDOUR::IO>, bool);
|
||||
~IOSelector ();
|
||||
|
||||
void set_state (
|
||||
boost::shared_ptr<ARDOUR::Bundle>,
|
||||
uint32_t,
|
||||
boost::shared_ptr<ARDOUR::Bundle>,
|
||||
uint32_t,
|
||||
bool,
|
||||
uint32_t
|
||||
);
|
||||
|
||||
State get_state (
|
||||
boost::shared_ptr<ARDOUR::Bundle>,
|
||||
uint32_t,
|
||||
boost::shared_ptr<ARDOUR::Bundle>,
|
||||
uint32_t
|
||||
) const;
|
||||
void set_state (ARDOUR::BundleChannel c[2], bool);
|
||||
State get_state (ARDOUR::BundleChannel c[2]) const;
|
||||
|
||||
void add_channel (boost::shared_ptr<ARDOUR::Bundle>);
|
||||
void remove_channel (boost::shared_ptr<ARDOUR::Bundle>, uint32_t);
|
||||
bool can_rename_channels () const {
|
||||
bool can_remove_channels (int d) const {
|
||||
return d == _ours;
|
||||
}
|
||||
void remove_channel (ARDOUR::BundleChannel);
|
||||
bool can_rename_channels (int d) const {
|
||||
return false;
|
||||
}
|
||||
|
||||
uint32_t n_rows () const;
|
||||
uint32_t maximum_rows () const;
|
||||
uint32_t minimum_rows () const;
|
||||
uint32_t n_io_ports () const;
|
||||
uint32_t maximum_io_ports () const;
|
||||
uint32_t minimum_io_ports () const;
|
||||
boost::shared_ptr<ARDOUR::IO> const io () { return _io; }
|
||||
void setup ();
|
||||
|
||||
bool find_inputs_for_io_outputs () const {
|
||||
return _find_inputs_for_io_outputs;
|
||||
}
|
||||
|
||||
private:
|
||||
ARDOUR::Session& _session;
|
||||
|
||||
int _other;
|
||||
int _ours;
|
||||
|
||||
boost::shared_ptr<ARDOUR::IO> _io;
|
||||
PortGroup* _port_group;
|
||||
boost::shared_ptr<PortGroup> _port_group;
|
||||
bool _find_inputs_for_io_outputs;
|
||||
|
||||
void ports_changed ();
|
||||
};
|
||||
|
|
|
|||
|
|
@ -49,7 +49,6 @@
|
|||
#include <pbd/fastlog.h>
|
||||
|
||||
#include "route_ui.h"
|
||||
#include "io_selector.h"
|
||||
#include "gain_meter.h"
|
||||
#include "panner_ui.h"
|
||||
#include "enums.h"
|
||||
|
|
@ -78,6 +77,7 @@ namespace Gtk {
|
|||
}
|
||||
|
||||
class Mixer_UI;
|
||||
class IOSelectorWindow;
|
||||
|
||||
class MixerStrip : public RouteUI, public Gtk::EventBox
|
||||
{
|
||||
|
|
|
|||
|
|
@ -40,6 +40,8 @@ PortGroup::add_bundle (boost::shared_ptr<ARDOUR::Bundle> b)
|
|||
{
|
||||
assert (b.get());
|
||||
_bundles.push_back (b);
|
||||
|
||||
Modified ();
|
||||
}
|
||||
|
||||
/** Add a port to a group.
|
||||
|
|
@ -49,6 +51,8 @@ void
|
|||
PortGroup::add_port (std::string const &p)
|
||||
{
|
||||
ports.push_back (p);
|
||||
|
||||
Modified ();
|
||||
}
|
||||
|
||||
void
|
||||
|
|
@ -56,6 +60,8 @@ PortGroup::clear ()
|
|||
{
|
||||
_bundles.clear ();
|
||||
ports.clear ();
|
||||
|
||||
Modified ();
|
||||
}
|
||||
|
||||
bool
|
||||
|
|
@ -84,60 +90,46 @@ PortGroup::only_bundle ()
|
|||
}
|
||||
|
||||
|
||||
/** PortGroupUI constructor.
|
||||
* @param m PortMatrix to work for.
|
||||
* @Param g PortGroup to represent.
|
||||
*/
|
||||
|
||||
PortGroupUI::PortGroupUI (PortMatrix* m, PortGroup* g)
|
||||
: _port_matrix (m)
|
||||
, _port_group (g)
|
||||
, _visibility_checkbutton (g->name)
|
||||
uint32_t
|
||||
PortGroup::total_ports () const
|
||||
{
|
||||
_port_group->set_visible (true);
|
||||
setup_visibility_checkbutton ();
|
||||
|
||||
_visibility_checkbutton.signal_toggled().connect (sigc::mem_fun (*this, &PortGroupUI::visibility_checkbutton_toggled));
|
||||
}
|
||||
|
||||
/** The visibility of a PortGroupUI has been toggled */
|
||||
void
|
||||
PortGroupUI::visibility_checkbutton_toggled ()
|
||||
{
|
||||
_port_group->set_visible (_visibility_checkbutton.get_active ());
|
||||
setup_visibility_checkbutton ();
|
||||
_port_matrix->setup ();
|
||||
}
|
||||
|
||||
/** Set up the visibility checkbutton according to PortGroup::visible */
|
||||
void
|
||||
PortGroupUI::setup_visibility_checkbutton ()
|
||||
{
|
||||
if (_visibility_checkbutton.get_active () != _port_group->visible()) {
|
||||
_visibility_checkbutton.set_active (_port_group->visible());
|
||||
uint32_t n = 0;
|
||||
for (ARDOUR::BundleList::const_iterator i = _bundles.begin(); i != _bundles.end(); ++i) {
|
||||
n += (*i)->nchannels ();
|
||||
}
|
||||
|
||||
n += ports.size();
|
||||
|
||||
return n;
|
||||
}
|
||||
|
||||
|
||||
/** PortGroupList constructor.
|
||||
* @param type Type of bundles to offer (audio or MIDI)
|
||||
* @param offer_inputs true to offer output bundles, otherwise false.
|
||||
*/
|
||||
|
||||
PortGroupList::PortGroupList (ARDOUR::DataType type, bool offer_inputs)
|
||||
: _type (type), _offer_inputs (offer_inputs), _bundles_dirty (true),
|
||||
_buss (_("Bus"), true),
|
||||
_track (_("Track"), true),
|
||||
_system (_("System"), true),
|
||||
_other (_("Other"), true)
|
||||
PortGroupList::PortGroupList ()
|
||||
: _type (ARDOUR::DataType::AUDIO), _bundles_dirty (true)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
void
|
||||
PortGroupList::set_type (ARDOUR::DataType t)
|
||||
{
|
||||
_type = t;
|
||||
clear ();
|
||||
}
|
||||
|
||||
/** Gather bundles from around the system and put them in this PortGroupList */
|
||||
void
|
||||
PortGroupList::gather (ARDOUR::Session& session)
|
||||
PortGroupList::gather (ARDOUR::Session& session, bool inputs)
|
||||
{
|
||||
clear_list ();
|
||||
clear ();
|
||||
|
||||
boost::shared_ptr<PortGroup> buss (new PortGroup (_("Buss")));
|
||||
boost::shared_ptr<PortGroup> track (new PortGroup (_("Track")));
|
||||
boost::shared_ptr<PortGroup> system (new PortGroup (_("System")));
|
||||
boost::shared_ptr<PortGroup> other (new PortGroup (_("Other")));
|
||||
|
||||
/* Find the bundles for routes. We take their bundles, copy them,
|
||||
and add ports from the route's processors */
|
||||
|
|
@ -148,7 +140,7 @@ PortGroupList::gather (ARDOUR::Session& session)
|
|||
/* Copy the appropriate bundle from the route */
|
||||
boost::shared_ptr<ARDOUR::Bundle> bundle (
|
||||
new ARDOUR::Bundle (
|
||||
_offer_inputs ? (*i)->bundle_for_inputs() : (*i)->bundle_for_outputs ()
|
||||
inputs ? (*i)->bundle_for_inputs() : (*i)->bundle_for_outputs ()
|
||||
)
|
||||
);
|
||||
|
||||
|
|
@ -163,7 +155,7 @@ PortGroupList::gather (ARDOUR::Session& session)
|
|||
boost::shared_ptr<ARDOUR::IOProcessor> iop = boost::dynamic_pointer_cast<ARDOUR::IOProcessor> (p);
|
||||
|
||||
if (iop) {
|
||||
boost::shared_ptr<ARDOUR::Bundle> pb = _offer_inputs ?
|
||||
boost::shared_ptr<ARDOUR::Bundle> pb = inputs ?
|
||||
iop->io()->bundle_for_inputs() : iop->io()->bundle_for_outputs();
|
||||
bundle->add_channels_from_bundle (pb);
|
||||
}
|
||||
|
|
@ -172,20 +164,20 @@ PortGroupList::gather (ARDOUR::Session& session)
|
|||
}
|
||||
|
||||
/* Work out which group to put this bundle in */
|
||||
PortGroup* g = 0;
|
||||
boost::shared_ptr<PortGroup> g;
|
||||
if (_type == ARDOUR::DataType::AUDIO) {
|
||||
|
||||
if (boost::dynamic_pointer_cast<ARDOUR::AudioTrack> (*i)) {
|
||||
g = &_track;
|
||||
g = track;
|
||||
} else if (!boost::dynamic_pointer_cast<ARDOUR::MidiTrack>(*i)) {
|
||||
g = &_buss;
|
||||
g = buss;
|
||||
}
|
||||
|
||||
|
||||
} else if (_type == ARDOUR::DataType::MIDI) {
|
||||
|
||||
if (boost::dynamic_pointer_cast<ARDOUR::MidiTrack> (*i)) {
|
||||
g = &_track;
|
||||
g = track;
|
||||
}
|
||||
|
||||
/* No MIDI busses yet */
|
||||
|
|
@ -200,14 +192,14 @@ PortGroupList::gather (ARDOUR::Session& session)
|
|||
|
||||
boost::shared_ptr<ARDOUR::BundleList> b = session.bundles ();
|
||||
for (ARDOUR::BundleList::iterator i = b->begin(); i != b->end(); ++i) {
|
||||
if ((*i)->ports_are_inputs() == _offer_inputs && (*i)->type() == _type) {
|
||||
_system.add_bundle (*i);
|
||||
if ((*i)->ports_are_inputs() == inputs && (*i)->type() == _type) {
|
||||
system->add_bundle (*i);
|
||||
}
|
||||
}
|
||||
|
||||
/* Now find all other ports that we haven't thought of yet */
|
||||
|
||||
const char **ports = session.engine().get_ports ("", _type.to_jack_type(), _offer_inputs ?
|
||||
const char **ports = session.engine().get_ports ("", _type.to_jack_type(), inputs ?
|
||||
JackPortIsInput : JackPortIsOutput);
|
||||
if (ports) {
|
||||
|
||||
|
|
@ -221,14 +213,14 @@ PortGroupList::gather (ARDOUR::Session& session)
|
|||
|
||||
std::string const p = ports[n];
|
||||
|
||||
if (!_system.has_port(p) && !_buss.has_port(p) && !_track.has_port(p) && !_other.has_port(p)) {
|
||||
if (!system->has_port(p) && !buss->has_port(p) && !track->has_port(p) && !other->has_port(p)) {
|
||||
|
||||
if (port_has_prefix (p, "system:") ||
|
||||
port_has_prefix (p, "alsa_pcm") ||
|
||||
port_has_prefix (p, "ardour:")) {
|
||||
_system.add_port (p);
|
||||
system->add_port (p);
|
||||
} else {
|
||||
_other.add_port (p);
|
||||
other->add_port (p);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -238,16 +230,10 @@ PortGroupList::gather (ARDOUR::Session& session)
|
|||
free (ports);
|
||||
}
|
||||
|
||||
push_back (&_system);
|
||||
push_back (&_buss);
|
||||
push_back (&_track);
|
||||
push_back (&_other);
|
||||
|
||||
for (iterator i = begin(); i != end(); ++i) {
|
||||
_visibility_connections.push_back (
|
||||
(*i)->VisibilityChanged.connect (sigc::mem_fun (*this, &PortGroupList::visibility_changed))
|
||||
);
|
||||
}
|
||||
add_group (system);
|
||||
add_group (buss);
|
||||
add_group (track);
|
||||
add_group (other);
|
||||
|
||||
_bundles_dirty = true;
|
||||
}
|
||||
|
|
@ -259,26 +245,12 @@ PortGroupList::port_has_prefix (const std::string& n, const std::string& p) cons
|
|||
}
|
||||
|
||||
|
||||
void
|
||||
PortGroupList::set_type (ARDOUR::DataType t)
|
||||
{
|
||||
_type = t;
|
||||
_bundles_dirty = true;
|
||||
}
|
||||
|
||||
void
|
||||
PortGroupList::set_offer_inputs (bool i)
|
||||
{
|
||||
_offer_inputs = i;
|
||||
_bundles_dirty = true;
|
||||
}
|
||||
|
||||
void
|
||||
PortGroupList::update_bundles () const
|
||||
{
|
||||
_bundles.clear ();
|
||||
|
||||
for (const_iterator i = begin (); i != end (); ++i) {
|
||||
for (PortGroupList::List::const_iterator i = begin (); i != end (); ++i) {
|
||||
if ((*i)->visible()) {
|
||||
|
||||
std::copy ((*i)->bundles().begin(), (*i)->bundles().end(), std::back_inserter (_bundles));
|
||||
|
|
@ -346,39 +318,9 @@ PortGroupList::common_prefix (std::vector<std::string> const & p) const
|
|||
}
|
||||
|
||||
void
|
||||
PortGroupList::visibility_changed ()
|
||||
PortGroupList::clear ()
|
||||
{
|
||||
VisibilityChanged ();
|
||||
}
|
||||
|
||||
void
|
||||
PortGroupList::take_visibility_from (PortGroupList const & o)
|
||||
{
|
||||
iterator i = begin ();
|
||||
const_iterator j = o.begin ();
|
||||
|
||||
while (i != end() && j != o.end()) {
|
||||
(*i)->set_visible ((*j)->visible());
|
||||
++i;
|
||||
++j;
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
PortGroupList::clear_list ()
|
||||
{
|
||||
clear ();
|
||||
|
||||
_buss.clear ();
|
||||
_track.clear ();
|
||||
_system.clear ();
|
||||
_other.clear ();
|
||||
|
||||
for (std::vector<sigc::connection>::iterator i = _visibility_connections.begin(); i != _visibility_connections.end(); ++i) {
|
||||
i->disconnect ();
|
||||
}
|
||||
|
||||
_visibility_connections.clear ();
|
||||
_groups.clear ();
|
||||
_bundles_dirty = true;
|
||||
}
|
||||
|
||||
|
|
@ -391,3 +333,31 @@ PortGroupList::bundles () const
|
|||
|
||||
return _bundles;
|
||||
}
|
||||
|
||||
uint32_t
|
||||
PortGroupList::total_visible_ports () const
|
||||
{
|
||||
uint32_t n = 0;
|
||||
|
||||
for (PortGroupList::List::const_iterator i = begin(); i != end(); ++i) {
|
||||
if ((*i)->visible()) {
|
||||
n += (*i)->total_ports ();
|
||||
}
|
||||
}
|
||||
|
||||
return n;
|
||||
}
|
||||
|
||||
void
|
||||
PortGroupList::group_modified ()
|
||||
{
|
||||
_bundles_dirty = true;
|
||||
}
|
||||
|
||||
void
|
||||
PortGroupList::add_group (boost::shared_ptr<PortGroup> g)
|
||||
{
|
||||
_groups.push_back (g);
|
||||
g->Modified.connect (sigc::mem_fun (*this, &PortGroupList::group_modified));
|
||||
_bundles_dirty = true;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -44,15 +44,15 @@ class PortGroup : public sigc::trackable
|
|||
public:
|
||||
/** PortGroup constructor.
|
||||
* @param n Name.
|
||||
* @param v true if group should be visible in the UI, otherwise false.
|
||||
*/
|
||||
PortGroup (std::string const & n, bool v)
|
||||
: name (n), _visible (v) {}
|
||||
PortGroup (std::string const & n)
|
||||
: name (n), _visible (true) {}
|
||||
|
||||
void add_bundle (boost::shared_ptr<ARDOUR::Bundle>);
|
||||
boost::shared_ptr<ARDOUR::Bundle> only_bundle ();
|
||||
void add_port (std::string const &);
|
||||
void clear ();
|
||||
uint32_t total_ports () const;
|
||||
|
||||
std::string name; ///< name for the group
|
||||
std::vector<std::string> ports;
|
||||
|
|
@ -67,69 +67,56 @@ public:
|
|||
|
||||
void set_visible (bool v) {
|
||||
_visible = v;
|
||||
VisibilityChanged ();
|
||||
Modified ();
|
||||
}
|
||||
|
||||
bool has_port (std::string const &) const;
|
||||
|
||||
sigc::signal<void> VisibilityChanged;
|
||||
sigc::signal<void> Modified;
|
||||
|
||||
private:
|
||||
ARDOUR::BundleList _bundles;
|
||||
bool _visible; ///< true if the group is visible in the UI
|
||||
};
|
||||
|
||||
/// The UI for a PortGroup
|
||||
class PortGroupUI
|
||||
{
|
||||
public:
|
||||
PortGroupUI (PortMatrix*, PortGroup*);
|
||||
|
||||
Gtk::Widget& visibility_checkbutton () {
|
||||
return _visibility_checkbutton;
|
||||
}
|
||||
|
||||
private:
|
||||
void visibility_checkbutton_toggled ();
|
||||
void setup_visibility_checkbutton ();
|
||||
|
||||
PortMatrix* _port_matrix; ///< the PortMatrix that we are working for
|
||||
PortGroup* _port_group; ///< the PortGroup that we are representing
|
||||
Gtk::CheckButton _visibility_checkbutton;
|
||||
};
|
||||
|
||||
/// A list of PortGroups
|
||||
class PortGroupList : public std::list<PortGroup*>, public sigc::trackable
|
||||
class PortGroupList
|
||||
{
|
||||
public:
|
||||
PortGroupList (ARDOUR::DataType, bool);
|
||||
PortGroupList ();
|
||||
|
||||
void gather (ARDOUR::Session &);
|
||||
typedef std::vector<boost::shared_ptr<PortGroup> > List;
|
||||
|
||||
void add_group (boost::shared_ptr<PortGroup>);
|
||||
void set_type (ARDOUR::DataType);
|
||||
void gather (ARDOUR::Session &, bool);
|
||||
void set_offer_inputs (bool);
|
||||
ARDOUR::BundleList const & bundles () const;
|
||||
void take_visibility_from (PortGroupList const &);
|
||||
void clear_list ();
|
||||
void clear ();
|
||||
uint32_t total_visible_ports () const;
|
||||
uint32_t size () const {
|
||||
return _groups.size();
|
||||
}
|
||||
|
||||
sigc::signal<void> VisibilityChanged;
|
||||
List::const_iterator begin () const {
|
||||
return _groups.begin();
|
||||
}
|
||||
|
||||
List::const_iterator end () const {
|
||||
return _groups.end();
|
||||
}
|
||||
|
||||
private:
|
||||
bool port_has_prefix (std::string const &, std::string const &) const;
|
||||
std::string common_prefix (std::vector<std::string> const &) const;
|
||||
void visibility_changed ();
|
||||
void update_bundles () const;
|
||||
void group_modified ();
|
||||
|
||||
ARDOUR::DataType _type;
|
||||
bool _offer_inputs;
|
||||
mutable ARDOUR::BundleList _bundles;
|
||||
mutable bool _bundles_dirty;
|
||||
|
||||
PortGroup _buss;
|
||||
PortGroup _track;
|
||||
PortGroup _system;
|
||||
PortGroup _other;
|
||||
|
||||
std::vector<sigc::connection> _visibility_connections;
|
||||
List _groups;
|
||||
};
|
||||
|
||||
#endif /* __gtk_ardour_port_group_h__ */
|
||||
|
|
|
|||
|
|
@ -21,6 +21,9 @@
|
|||
#include <gtkmm/scrolledwindow.h>
|
||||
#include <gtkmm/adjustment.h>
|
||||
#include <gtkmm/label.h>
|
||||
#include <gtkmm/menu.h>
|
||||
#include <gtkmm/menushell.h>
|
||||
#include <gtkmm/menu_elems.h>
|
||||
#include "ardour/bundle.h"
|
||||
#include "ardour/types.h"
|
||||
#include "ardour/session.h"
|
||||
|
|
@ -31,59 +34,50 @@
|
|||
/** PortMatrix constructor.
|
||||
* @param session Our session.
|
||||
* @param type Port type that we are handling.
|
||||
* @param offer_inputs true to offer inputs, otherwise false.
|
||||
*/
|
||||
PortMatrix::PortMatrix (ARDOUR::Session& session, ARDOUR::DataType type, bool offer_inputs)
|
||||
: _row_ports (type, !offer_inputs),
|
||||
_column_ports (type, offer_inputs),
|
||||
_session (session),
|
||||
_offer_inputs (offer_inputs),
|
||||
PortMatrix::PortMatrix (ARDOUR::Session& session, ARDOUR::DataType type)
|
||||
: _session (session),
|
||||
_type (type),
|
||||
_body (this, offer_inputs ? PortMatrixBody::BOTTOM_AND_LEFT : PortMatrixBody::TOP_AND_RIGHT)
|
||||
_body (this),
|
||||
_menu (0),
|
||||
_setup_once (false),
|
||||
_arrangement (TOP_TO_RIGHT),
|
||||
_row_index (0),
|
||||
_column_index (1)
|
||||
{
|
||||
setup ();
|
||||
_ports[0].set_type (type);
|
||||
_ports[1].set_type (type);
|
||||
|
||||
/* checkbuttons for visibility of groups */
|
||||
Gtk::HBox* visibility_buttons = Gtk::manage (new Gtk::HBox);
|
||||
|
||||
visibility_buttons->pack_start (*Gtk::manage (new Gtk::Label (_("Show:"))), Gtk::PACK_SHRINK);
|
||||
|
||||
for (std::list<PortGroup*>::iterator i = _column_ports.begin(); i != _column_ports.end(); ++i) {
|
||||
_port_group_uis.push_back (new PortGroupUI (this, *i));
|
||||
}
|
||||
|
||||
for (std::list<PortGroupUI*>::iterator i = _port_group_uis.begin(); i != _port_group_uis.end(); ++i) {
|
||||
visibility_buttons->pack_start ((*i)->visibility_checkbutton(), Gtk::PACK_SHRINK);
|
||||
}
|
||||
|
||||
pack_start (*visibility_buttons, Gtk::PACK_SHRINK);
|
||||
pack_start (_hscroll, Gtk::PACK_SHRINK);
|
||||
Gtk::HBox* hbox = Gtk::manage (new Gtk::HBox);
|
||||
hbox->pack_start (_body);
|
||||
hbox->pack_start (_vscroll, Gtk::PACK_SHRINK);
|
||||
pack_start (*hbox);
|
||||
_row_visibility_box.pack_start (_row_visibility_label, Gtk::PACK_SHRINK);
|
||||
_column_visibility_box.pack_start (_column_visibility_label, Gtk::PACK_SHRINK);
|
||||
|
||||
_hscroll.signal_value_changed().connect (sigc::mem_fun (*this, &PortMatrix::hscroll_changed));
|
||||
_vscroll.signal_value_changed().connect (sigc::mem_fun (*this, &PortMatrix::vscroll_changed));
|
||||
setup_scrollbars ();
|
||||
|
||||
/* watch for routes being added or removed */
|
||||
_session.RouteAdded.connect (sigc::hide (sigc::mem_fun (*this, &PortMatrix::routes_changed)));
|
||||
routes_changed ();
|
||||
|
||||
/* XXX hard-coded initial size suggestion */
|
||||
set_size_request (400, 200);
|
||||
reconnect_to_routes ();
|
||||
|
||||
show_all ();
|
||||
}
|
||||
|
||||
PortMatrix::~PortMatrix ()
|
||||
{
|
||||
for (std::list<PortGroupUI*>::iterator i = _port_group_uis.begin(); i != _port_group_uis.end(); ++i) {
|
||||
for (std::vector<Gtk::CheckButton*>::iterator i = _column_visibility_buttons.begin(); i != _column_visibility_buttons.end(); ++i) {
|
||||
delete *i;
|
||||
}
|
||||
|
||||
for (std::vector<Gtk::CheckButton*>::iterator i = _row_visibility_buttons.begin(); i != _row_visibility_buttons.end(); ++i) {
|
||||
delete *i;
|
||||
}
|
||||
|
||||
delete _menu;
|
||||
}
|
||||
|
||||
/** Disconnect from and reconnect to routes' signals that we need to watch for things that affect the matrix */
|
||||
void
|
||||
PortMatrix::routes_changed ()
|
||||
PortMatrix::reconnect_to_routes ()
|
||||
{
|
||||
for (std::vector<sigc::connection>::iterator i = _route_connections.begin(); i != _route_connections.end(); ++i) {
|
||||
i->disconnect ();
|
||||
|
|
@ -95,34 +89,120 @@ PortMatrix::routes_changed ()
|
|||
(*i)->processors_changed.connect (sigc::mem_fun (*this, &PortMatrix::setup))
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
/** A route has been added to or removed from the session */
|
||||
void
|
||||
PortMatrix::routes_changed ()
|
||||
{
|
||||
reconnect_to_routes ();
|
||||
setup ();
|
||||
}
|
||||
|
||||
/** Set up everything that changes about the matrix */
|
||||
void
|
||||
PortMatrix::setup ()
|
||||
{
|
||||
_column_ports.gather (_session);
|
||||
_body.setup (_row_ports, _column_ports);
|
||||
select_arrangement ();
|
||||
_body.setup ();
|
||||
setup_scrollbars ();
|
||||
queue_draw ();
|
||||
}
|
||||
|
||||
void
|
||||
PortMatrix::set_offer_inputs (bool s)
|
||||
{
|
||||
_offer_inputs = s;
|
||||
_column_ports.set_offer_inputs (s);
|
||||
_row_ports.set_offer_inputs (!s);
|
||||
setup ();
|
||||
if (_setup_once) {
|
||||
|
||||
/* we've set up before, so we need to clean up before re-setting-up */
|
||||
|
||||
for (std::vector<Gtk::CheckButton*>::iterator i = _column_visibility_buttons.begin(); i != _column_visibility_buttons.end(); ++i) {
|
||||
_column_visibility_box.remove (**i);
|
||||
delete *i;
|
||||
}
|
||||
|
||||
_column_visibility_buttons.clear ();
|
||||
|
||||
for (std::vector<Gtk::CheckButton*>::iterator i = _row_visibility_buttons.begin(); i != _row_visibility_buttons.end(); ++i) {
|
||||
_row_visibility_box.remove (**i);
|
||||
delete *i;
|
||||
}
|
||||
|
||||
_row_visibility_buttons.clear ();
|
||||
|
||||
_scroller_table.remove (_vscroll);
|
||||
_scroller_table.remove (_body);
|
||||
_scroller_table.remove (_hscroll);
|
||||
|
||||
_main_hbox.remove (_scroller_table);
|
||||
_main_hbox.remove (_row_visibility_box);
|
||||
|
||||
remove (_column_visibility_box);
|
||||
remove (_main_hbox);
|
||||
}
|
||||
|
||||
if (_column_index == 0) {
|
||||
_column_visibility_label.set_text (_("Show Outputs"));
|
||||
_row_visibility_label.set_text (_("Show Inputs"));
|
||||
} else {
|
||||
_column_visibility_label.set_text (_("Show Inputs"));
|
||||
_row_visibility_label.set_text (_("Show Outputs"));
|
||||
}
|
||||
|
||||
/* only show visibility checkbuttons if there is more than one group */
|
||||
if (columns()->size() > 1) {
|
||||
for (PortGroupList::List::const_iterator i = columns()->begin(); i != columns()->end(); ++i) {
|
||||
Gtk::CheckButton* b = new Gtk::CheckButton ((*i)->name);
|
||||
b->set_active ((*i)->visible());
|
||||
boost::weak_ptr<PortGroup> w (*i);
|
||||
b->signal_toggled().connect (sigc::bind (sigc::mem_fun (*this, &PortMatrix::visibility_toggled), w, b));
|
||||
_column_visibility_buttons.push_back (b);
|
||||
_column_visibility_box.pack_start (*b, Gtk::PACK_SHRINK);
|
||||
}
|
||||
}
|
||||
|
||||
if (rows()->size() > 1) {
|
||||
for (PortGroupList::List::const_iterator i = rows()->begin(); i != rows()->end(); ++i) {
|
||||
Gtk::CheckButton* b = new Gtk::CheckButton ((*i)->name);
|
||||
b->set_active ((*i)->visible());
|
||||
boost::weak_ptr<PortGroup> w (*i);
|
||||
b->signal_toggled().connect (sigc::bind (sigc::mem_fun (*this, &PortMatrix::visibility_toggled), w, b));
|
||||
_row_visibility_buttons.push_back (b);
|
||||
_row_visibility_box.pack_start (*b, Gtk::PACK_SHRINK);
|
||||
}
|
||||
}
|
||||
|
||||
if (_arrangement == TOP_TO_RIGHT) {
|
||||
|
||||
_scroller_table.attach (_hscroll, 0, 1, 0, 1, Gtk::FILL | Gtk::EXPAND, Gtk::SHRINK);
|
||||
_scroller_table.attach (_body, 0, 1, 1, 2);
|
||||
_scroller_table.attach (_vscroll, 1, 2, 1, 2, Gtk::SHRINK);
|
||||
|
||||
_main_hbox.pack_start (_scroller_table);
|
||||
_main_hbox.pack_start (_row_visibility_box, Gtk::PACK_SHRINK);
|
||||
|
||||
pack_start (_column_visibility_box, Gtk::PACK_SHRINK);
|
||||
pack_start (_main_hbox);
|
||||
|
||||
} else {
|
||||
_scroller_table.attach (_vscroll, 0, 1, 0, 1, Gtk::SHRINK);
|
||||
_scroller_table.attach (_body, 1, 2, 0, 1);
|
||||
_scroller_table.attach (_hscroll, 1, 2, 1, 2, Gtk::FILL | Gtk::EXPAND, Gtk::SHRINK);
|
||||
|
||||
_main_hbox.pack_start (_row_visibility_box, Gtk::PACK_SHRINK);
|
||||
_main_hbox.pack_start (_scroller_table);
|
||||
|
||||
pack_start (_main_hbox);
|
||||
pack_start (_column_visibility_box, Gtk::PACK_SHRINK);
|
||||
}
|
||||
|
||||
_setup_once = true;
|
||||
|
||||
show_all ();
|
||||
}
|
||||
|
||||
void
|
||||
PortMatrix::set_type (ARDOUR::DataType t)
|
||||
{
|
||||
_type = t;
|
||||
_column_ports.set_type (t);
|
||||
_row_ports.set_type (t);
|
||||
_ports[0].set_type (_type);
|
||||
_ports[1].set_type (_type);
|
||||
setup ();
|
||||
}
|
||||
|
||||
|
|
@ -156,23 +236,166 @@ PortMatrix::setup_scrollbars ()
|
|||
a->set_page_increment (128);
|
||||
}
|
||||
|
||||
/** Disassociate all of our ports from each other */
|
||||
void
|
||||
PortMatrix::disassociate_all ()
|
||||
{
|
||||
ARDOUR::BundleList c = _column_ports.bundles ();
|
||||
ARDOUR::BundleList r = _row_ports.bundles ();
|
||||
ARDOUR::BundleList a = _ports[0].bundles ();
|
||||
ARDOUR::BundleList b = _ports[1].bundles ();
|
||||
|
||||
for (ARDOUR::BundleList::iterator i = c.begin(); i != c.end(); ++i) {
|
||||
for (ARDOUR::BundleList::iterator i = a.begin(); i != a.end(); ++i) {
|
||||
for (uint32_t j = 0; j < (*i)->nchannels(); ++j) {
|
||||
for (uint32_t k = 0; k < r.front()->nchannels(); ++k) {
|
||||
for (ARDOUR::BundleList::iterator k = b.begin(); k != b.end(); ++k) {
|
||||
for (uint32_t l = 0; l < (*k)->nchannels(); ++l) {
|
||||
|
||||
set_state (
|
||||
r.front(), k, *i, j, false, 0
|
||||
);
|
||||
ARDOUR::BundleChannel c[2] = {
|
||||
ARDOUR::BundleChannel (*i, j),
|
||||
ARDOUR::BundleChannel (*k, l)
|
||||
};
|
||||
|
||||
set_state (c, false);
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
_body.rebuild_and_draw_grid ();
|
||||
}
|
||||
|
||||
/* Decide how to arrange the components of the matrix */
|
||||
void
|
||||
PortMatrix::select_arrangement ()
|
||||
{
|
||||
uint32_t const N[2] = {
|
||||
_ports[0].total_visible_ports (),
|
||||
_ports[1].total_visible_ports ()
|
||||
};
|
||||
|
||||
/* The list with the most ports goes on left or right, so that the most port
|
||||
names are printed horizontally and hence more readable. However we also
|
||||
maintain notional `signal flow' vaguely from left to right. Subclasses
|
||||
should choose where to put ports based on signal flowing from _ports[0]
|
||||
to _ports[1] */
|
||||
|
||||
if (N[0] > N[1]) {
|
||||
|
||||
_row_index = 0;
|
||||
_column_index = 1;
|
||||
_arrangement = LEFT_TO_BOTTOM;
|
||||
|
||||
} else {
|
||||
|
||||
_row_index = 1;
|
||||
_column_index = 0;
|
||||
_arrangement = TOP_TO_RIGHT;
|
||||
}
|
||||
}
|
||||
|
||||
/** @return columns list */
|
||||
PortGroupList const *
|
||||
PortMatrix::columns () const
|
||||
{
|
||||
return &_ports[_column_index];
|
||||
}
|
||||
|
||||
/* @return rows list */
|
||||
PortGroupList const *
|
||||
PortMatrix::rows () const
|
||||
{
|
||||
return &_ports[_row_index];
|
||||
}
|
||||
|
||||
/** A group visibility checkbutton has been toggled.
|
||||
* @param w Group.
|
||||
* @param b Button.
|
||||
*/
|
||||
void
|
||||
PortMatrix::visibility_toggled (boost::weak_ptr<PortGroup> w, Gtk::CheckButton* b)
|
||||
{
|
||||
boost::shared_ptr<PortGroup> g = w.lock ();
|
||||
if (!g) {
|
||||
return;
|
||||
}
|
||||
|
||||
g->set_visible (b->get_active());
|
||||
_body.setup ();
|
||||
setup_scrollbars ();
|
||||
queue_draw ();
|
||||
}
|
||||
|
||||
void
|
||||
PortMatrix::popup_channel_context_menu (int dim, uint32_t N, uint32_t t)
|
||||
{
|
||||
delete _menu;
|
||||
|
||||
_menu = new Gtk::Menu;
|
||||
_menu->set_name ("ArdourContextMenu");
|
||||
|
||||
Gtk::Menu_Helpers::MenuList& items = _menu->items ();
|
||||
|
||||
ARDOUR::BundleChannel bc;
|
||||
|
||||
ARDOUR::BundleList const r = _ports[dim].bundles();
|
||||
for (ARDOUR::BundleList::const_iterator i = r.begin(); i != r.end(); ++i) {
|
||||
if (N < (*i)->nchannels ()) {
|
||||
bc = ARDOUR::BundleChannel (*i, N);
|
||||
break;
|
||||
} else {
|
||||
N -= (*i)->nchannels ();
|
||||
}
|
||||
}
|
||||
|
||||
if (bc.bundle) {
|
||||
char buf [64];
|
||||
|
||||
if (can_rename_channels (dim)) {
|
||||
snprintf (buf, sizeof (buf), _("Rename '%s'..."), bc.bundle->channel_name (bc.channel).c_str());
|
||||
boost::weak_ptr<ARDOUR::Bundle> w (bc.bundle);
|
||||
items.push_back (
|
||||
Gtk::Menu_Helpers::MenuElem (
|
||||
buf,
|
||||
sigc::bind (sigc::mem_fun (*this, &PortMatrix::rename_channel_proxy), w, bc.channel)
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
if (can_remove_channels (dim)) {
|
||||
snprintf (buf, sizeof (buf), _("Remove '%s'"), bc.bundle->channel_name (bc.channel).c_str());
|
||||
boost::weak_ptr<ARDOUR::Bundle> w (bc.bundle);
|
||||
items.push_back (
|
||||
Gtk::Menu_Helpers::MenuElem (
|
||||
buf,
|
||||
sigc::bind (sigc::mem_fun (*this, &PortMatrix::remove_channel_proxy), w, bc.channel)
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
_menu->popup (1, t);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
PortMatrix::remove_channel_proxy (boost::weak_ptr<ARDOUR::Bundle> b, uint32_t c)
|
||||
{
|
||||
boost::shared_ptr<ARDOUR::Bundle> sb = b.lock ();
|
||||
if (!sb) {
|
||||
return;
|
||||
}
|
||||
|
||||
remove_channel (ARDOUR::BundleChannel (sb, c));
|
||||
|
||||
}
|
||||
|
||||
void
|
||||
PortMatrix::rename_channel_proxy (boost::weak_ptr<ARDOUR::Bundle> b, uint32_t c)
|
||||
{
|
||||
boost::shared_ptr<ARDOUR::Bundle> sb = b.lock ();
|
||||
if (!sb) {
|
||||
return;
|
||||
}
|
||||
|
||||
rename_channel (ARDOUR::BundleChannel (sb, c));
|
||||
}
|
||||
|
|
|
|||
|
|
@ -23,6 +23,9 @@
|
|||
#include <list>
|
||||
#include <gtkmm/box.h>
|
||||
#include <gtkmm/scrollbar.h>
|
||||
#include <gtkmm/table.h>
|
||||
#include <gtkmm/label.h>
|
||||
#include <gtkmm/checkbutton.h>
|
||||
#include <boost/shared_ptr.hpp>
|
||||
#include "port_matrix_body.h"
|
||||
#include "port_group.h"
|
||||
|
|
@ -31,12 +34,9 @@
|
|||
* associations between one set of ports and another. e.g. to connect
|
||||
* things together.
|
||||
*
|
||||
* The columns are labelled with various ports from around Ardour and the
|
||||
* system.
|
||||
*
|
||||
* It is made up of a body, PortMatrixBody, which is rendered using cairo,
|
||||
* and some scrollbars. All of this is arranged inside the VBox that we
|
||||
* inherit from.
|
||||
* and some scrollbars and other stuff. All of this is arranged inside the
|
||||
* VBox that we inherit from.
|
||||
*/
|
||||
|
||||
namespace ARDOUR {
|
||||
|
|
@ -46,22 +46,66 @@ namespace ARDOUR {
|
|||
class PortMatrix : public Gtk::VBox
|
||||
{
|
||||
public:
|
||||
PortMatrix (ARDOUR::Session&, ARDOUR::DataType, bool);
|
||||
PortMatrix (ARDOUR::Session&, ARDOUR::DataType);
|
||||
~PortMatrix ();
|
||||
|
||||
virtual void setup ();
|
||||
void set_offer_inputs (bool);
|
||||
void set_type (ARDOUR::DataType);
|
||||
|
||||
ARDOUR::DataType type () const {
|
||||
return _type;
|
||||
}
|
||||
|
||||
bool offering_input () const {
|
||||
return _offer_inputs;
|
||||
void disassociate_all ();
|
||||
void setup_scrollbars ();
|
||||
void popup_channel_context_menu (int, uint32_t, uint32_t);
|
||||
|
||||
enum Arrangement {
|
||||
TOP_TO_RIGHT, ///< column labels on top, row labels to the right
|
||||
LEFT_TO_BOTTOM ///< row labels to the left, column labels on the bottom
|
||||
};
|
||||
|
||||
/** @return Arrangement in use */
|
||||
Arrangement arrangement () const {
|
||||
return _arrangement;
|
||||
}
|
||||
|
||||
void disassociate_all ();
|
||||
PortGroupList const * columns () const;
|
||||
|
||||
/** @return index into the _ports array for the list which is displayed as columns */
|
||||
int column_index () const {
|
||||
return _column_index;
|
||||
}
|
||||
|
||||
PortGroupList const * rows () const;
|
||||
|
||||
/** @return index into the _ports array for the list which is displayed as rows */
|
||||
int row_index () const {
|
||||
return _row_index;
|
||||
}
|
||||
|
||||
virtual void setup ();
|
||||
|
||||
/** @param c Channels; where c[0] is from _ports[0] and c[1] is from _ports[1].
|
||||
* @param s New state.
|
||||
*/
|
||||
virtual void set_state (ARDOUR::BundleChannel c[2], bool s) = 0;
|
||||
|
||||
enum State {
|
||||
ASSOCIATED, ///< the ports are associaed
|
||||
NOT_ASSOCIATED, ///< the ports are not associated
|
||||
UNKNOWN ///< we don't know anything about these two ports' relationship
|
||||
};
|
||||
|
||||
/** @param c Channels; where c[0] is from _ports[0] and c[1] is from _ports[1].
|
||||
* @return state
|
||||
*/
|
||||
virtual State get_state (ARDOUR::BundleChannel c[2]) const = 0;
|
||||
|
||||
virtual void add_channel (boost::shared_ptr<ARDOUR::Bundle>) = 0;
|
||||
virtual bool can_remove_channels (int) const = 0;
|
||||
virtual void remove_channel (ARDOUR::BundleChannel) = 0;
|
||||
virtual bool can_rename_channels (int) const = 0;
|
||||
virtual void rename_channel (ARDOUR::BundleChannel) {}
|
||||
|
||||
enum Result {
|
||||
Cancelled,
|
||||
|
|
@ -70,70 +114,48 @@ public:
|
|||
|
||||
sigc::signal<void, Result> Finished;
|
||||
|
||||
/** @param ab Our bundle.
|
||||
* @param ac Channel on our bundle.
|
||||
* @param bb Other bundle.
|
||||
* @arapm bc Channel on other bundle.
|
||||
* @param s New state.
|
||||
* @param k XXX
|
||||
*/
|
||||
virtual void set_state (
|
||||
boost::shared_ptr<ARDOUR::Bundle> ab,
|
||||
uint32_t ac,
|
||||
boost::shared_ptr<ARDOUR::Bundle> bb,
|
||||
uint32_t bc,
|
||||
bool s,
|
||||
uint32_t k
|
||||
) = 0;
|
||||
|
||||
enum State {
|
||||
ASSOCIATED,
|
||||
NOT_ASSOCIATED,
|
||||
UNKNOWN
|
||||
};
|
||||
|
||||
/** @param ab Our bundle.
|
||||
* @param ac Channel on our bundle.
|
||||
* @param bb Other bundle.
|
||||
* @arapm bc Channel on other bundle.
|
||||
* @return state
|
||||
*/
|
||||
virtual State get_state (
|
||||
boost::shared_ptr<ARDOUR::Bundle> ab,
|
||||
uint32_t ac,
|
||||
boost::shared_ptr<ARDOUR::Bundle> bb,
|
||||
uint32_t bc
|
||||
) const = 0;
|
||||
|
||||
virtual void add_channel (boost::shared_ptr<ARDOUR::Bundle>) = 0;
|
||||
virtual void remove_channel (boost::shared_ptr<ARDOUR::Bundle>, uint32_t) = 0;
|
||||
virtual bool can_rename_channels () const = 0;
|
||||
virtual void rename_channel (boost::shared_ptr<ARDOUR::Bundle>, uint32_t) {}
|
||||
|
||||
void setup_scrollbars ();
|
||||
|
||||
protected:
|
||||
|
||||
PortGroupList _row_ports;
|
||||
PortGroupList _column_ports;
|
||||
/** We have two port group lists. One will be presented on the rows of the matrix,
|
||||
the other on the columns. The PortMatrix chooses the arrangement based on which has
|
||||
more ports in it. Subclasses must fill these two lists with the port groups that they
|
||||
wish to present. The PortMatrix will arrange its layout such that signal flow is vaguely
|
||||
from left to right as you go from list 0 to list 1. Hence subclasses which deal with
|
||||
inputs and outputs should put outputs in list 0 and inputs in list 1. */
|
||||
PortGroupList _ports[2];
|
||||
ARDOUR::Session& _session;
|
||||
|
||||
private:
|
||||
|
||||
void hscroll_changed ();
|
||||
void vscroll_changed ();
|
||||
void routes_changed ();
|
||||
void reconnect_to_routes ();
|
||||
void visibility_toggled (boost::weak_ptr<PortGroup>, Gtk::CheckButton *);
|
||||
void select_arrangement ();
|
||||
void remove_channel_proxy (boost::weak_ptr<ARDOUR::Bundle>, uint32_t);
|
||||
void rename_channel_proxy (boost::weak_ptr<ARDOUR::Bundle>, uint32_t);
|
||||
|
||||
ARDOUR::Session& _session;
|
||||
/// true to offer inputs, otherwise false
|
||||
bool _offer_inputs;
|
||||
/// port type that we are working with
|
||||
ARDOUR::DataType _type;
|
||||
std::vector<sigc::connection> _route_connections;
|
||||
|
||||
PortMatrixBody _body;
|
||||
Gtk::HScrollbar _hscroll;
|
||||
Gtk::VScrollbar _vscroll;
|
||||
std::list<PortGroupUI*> _port_group_uis;
|
||||
std::vector<sigc::connection> _route_connections;
|
||||
Gtk::HBox _main_hbox;
|
||||
Gtk::HBox _column_visibility_box;
|
||||
Gtk::Label _column_visibility_label;
|
||||
std::vector<Gtk::CheckButton*> _column_visibility_buttons;
|
||||
Gtk::VBox _row_visibility_box;
|
||||
Gtk::Label _row_visibility_label;
|
||||
std::vector<Gtk::CheckButton*> _row_visibility_buttons;
|
||||
Gtk::Table _scroller_table;
|
||||
Gtk::Menu* _menu;
|
||||
bool _setup_once;
|
||||
Arrangement _arrangement;
|
||||
int _row_index;
|
||||
int _column_index;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
|||
|
|
@ -23,17 +23,14 @@
|
|||
#include "port_matrix_body.h"
|
||||
#include "port_matrix.h"
|
||||
|
||||
PortMatrixBody::PortMatrixBody (PortMatrix* p, Arrangement a)
|
||||
: _port_matrix (p),
|
||||
_column_labels (this, a == TOP_AND_RIGHT ? PortMatrixColumnLabels::TOP : PortMatrixColumnLabels::BOTTOM),
|
||||
_row_labels (p, this, a == BOTTOM_AND_LEFT ? PortMatrixRowLabels::LEFT : PortMatrixRowLabels::RIGHT),
|
||||
PortMatrixBody::PortMatrixBody (PortMatrix* p)
|
||||
: _matrix (p),
|
||||
_column_labels (p, this),
|
||||
_row_labels (p, this),
|
||||
_grid (p, this),
|
||||
_arrangement (a),
|
||||
_xoffset (0),
|
||||
_yoffset (0),
|
||||
_pointer_inside (false),
|
||||
_column_ports (_port_matrix->type(), _port_matrix->offering_input()),
|
||||
_row_ports (_port_matrix->type(), !_port_matrix->offering_input())
|
||||
_pointer_inside (false)
|
||||
{
|
||||
modify_bg (Gtk::STATE_NORMAL, Gdk::Color ("#00000"));
|
||||
add_events (Gdk::ENTER_NOTIFY_MASK | Gdk::LEAVE_NOTIFY_MASK | Gdk::POINTER_MOTION_MASK);
|
||||
|
|
@ -115,21 +112,23 @@ PortMatrixBody::on_size_request (Gtk::Requisition *req)
|
|||
std::pair<int, int> const row = _row_labels.dimensions ();
|
||||
std::pair<int, int> const grid = _grid.dimensions ();
|
||||
|
||||
req->width = std::max (col.first, grid.first + row.first);
|
||||
req->height = col.second + grid.second;
|
||||
/* don't ask for the maximum size of our contents, otherwise GTK won't
|
||||
let the containing window shrink below this size */
|
||||
|
||||
req->width = std::min (512, std::max (col.first, grid.first + row.first));
|
||||
req->height = std::min (512, col.second + grid.second);
|
||||
}
|
||||
|
||||
void
|
||||
PortMatrixBody::on_size_allocate (Gtk::Allocation& alloc)
|
||||
{
|
||||
Gtk::EventBox::on_size_allocate (alloc);
|
||||
set_allocation (alloc);
|
||||
|
||||
_alloc_width = alloc.get_width ();
|
||||
_alloc_height = alloc.get_height ();
|
||||
|
||||
compute_rectangles ();
|
||||
_port_matrix->setup_scrollbars ();
|
||||
_matrix->setup_scrollbars ();
|
||||
}
|
||||
|
||||
void
|
||||
|
|
@ -144,7 +143,7 @@ PortMatrixBody::compute_rectangles ()
|
|||
Gdk::Rectangle row_rect;
|
||||
Gdk::Rectangle grid_rect;
|
||||
|
||||
if (_arrangement == TOP_AND_RIGHT) {
|
||||
if (_matrix->arrangement() == PortMatrix::TOP_TO_RIGHT) {
|
||||
|
||||
/* build from top left */
|
||||
|
||||
|
|
@ -187,7 +186,7 @@ PortMatrixBody::compute_rectangles ()
|
|||
row_rect.set_width (_alloc_width - x);
|
||||
|
||||
|
||||
} else if (_arrangement == BOTTOM_AND_LEFT) {
|
||||
} else if (_matrix->arrangement() == PortMatrix::LEFT_TO_BOTTOM) {
|
||||
|
||||
/* build from bottom right */
|
||||
|
||||
|
|
@ -233,18 +232,18 @@ PortMatrixBody::compute_rectangles ()
|
|||
}
|
||||
|
||||
void
|
||||
PortMatrixBody::setup (PortGroupList const& row, PortGroupList const& column)
|
||||
PortMatrixBody::setup ()
|
||||
{
|
||||
/* Discard any old connections to bundles */
|
||||
|
||||
for (std::list<sigc::connection>::iterator i = _bundle_connections.begin(); i != _bundle_connections.end(); ++i) {
|
||||
i->disconnect ();
|
||||
}
|
||||
|
||||
_bundle_connections.clear ();
|
||||
|
||||
_row_ports = row;
|
||||
_column_ports = column;
|
||||
/* Connect to bundles so that we find out when their names change */
|
||||
|
||||
ARDOUR::BundleList r = _row_ports.bundles ();
|
||||
ARDOUR::BundleList r = _matrix->rows()->bundles ();
|
||||
for (ARDOUR::BundleList::iterator i = r.begin(); i != r.end(); ++i) {
|
||||
|
||||
_bundle_connections.push_back (
|
||||
|
|
@ -253,7 +252,7 @@ PortMatrixBody::setup (PortGroupList const& row, PortGroupList const& column)
|
|||
|
||||
}
|
||||
|
||||
ARDOUR::BundleList c = _column_ports.bundles ();
|
||||
ARDOUR::BundleList c = _matrix->columns()->bundles ();
|
||||
for (ARDOUR::BundleList::iterator i = c.begin(); i != c.end(); ++i) {
|
||||
_bundle_connections.push_back (
|
||||
(*i)->NameChanged.connect (sigc::mem_fun (*this, &PortMatrixBody::rebuild_and_draw_column_labels))
|
||||
|
|
@ -264,6 +263,13 @@ PortMatrixBody::setup (PortGroupList const& row, PortGroupList const& column)
|
|||
_row_labels.setup ();
|
||||
_grid.setup ();
|
||||
|
||||
set_mouseover (
|
||||
PortMatrixNode (
|
||||
ARDOUR::BundleChannel (boost::shared_ptr<ARDOUR::Bundle> (), 0),
|
||||
ARDOUR::BundleChannel (boost::shared_ptr<ARDOUR::Bundle> (), 0)
|
||||
)
|
||||
);
|
||||
|
||||
compute_rectangles ();
|
||||
}
|
||||
|
||||
|
|
@ -325,10 +331,13 @@ PortMatrixBody::on_button_press_event (GdkEventButton* ev)
|
|||
ev->button, ev->time
|
||||
);
|
||||
|
||||
} else {
|
||||
|
||||
return false;
|
||||
} else if (Gdk::Region (_column_labels.parent_rectangle()).point_in (ev->x, ev->y)) {
|
||||
|
||||
_column_labels.button_press (
|
||||
_column_labels.parent_to_component_x (ev->x),
|
||||
_column_labels.parent_to_component_y (ev->y),
|
||||
ev->button, ev->time
|
||||
);
|
||||
}
|
||||
|
||||
return true;
|
||||
|
|
|
|||
|
|
@ -30,29 +30,13 @@ class PortMatrix;
|
|||
|
||||
/** The main body of the port matrix. It is made up of three parts:
|
||||
* column labels, grid and row labels, each drawn using cairo.
|
||||
* This class handles the arrangement of these parts.
|
||||
*/
|
||||
class PortMatrixBody : public Gtk::EventBox
|
||||
{
|
||||
public:
|
||||
enum Arrangement {
|
||||
TOP_AND_RIGHT,
|
||||
BOTTOM_AND_LEFT
|
||||
};
|
||||
PortMatrixBody (PortMatrix *);
|
||||
|
||||
PortMatrixBody (PortMatrix *, Arrangement);
|
||||
|
||||
/** @return ports to offer for columns */
|
||||
PortGroupList const & column_ports () {
|
||||
return _column_ports;
|
||||
}
|
||||
|
||||
/** @return ports to offer for rows */
|
||||
PortGroupList const & row_ports () {
|
||||
return _row_ports;
|
||||
}
|
||||
|
||||
void setup (PortGroupList const &, PortGroupList const &);
|
||||
void setup ();
|
||||
|
||||
uint32_t full_scroll_width ();
|
||||
uint32_t alloc_scroll_width ();
|
||||
|
|
@ -75,10 +59,6 @@ public:
|
|||
return _mouseover;
|
||||
}
|
||||
|
||||
Arrangement arrangement () const {
|
||||
return _arrangement;
|
||||
}
|
||||
|
||||
protected:
|
||||
bool on_expose_event (GdkEventExpose *);
|
||||
void on_size_request (Gtk::Requisition *);
|
||||
|
|
@ -93,12 +73,11 @@ private:
|
|||
void rebuild_and_draw_row_labels ();
|
||||
void update_bundles ();
|
||||
|
||||
PortMatrix* _port_matrix;
|
||||
PortMatrix* _matrix;
|
||||
PortMatrixColumnLabels _column_labels;
|
||||
PortMatrixRowLabels _row_labels;
|
||||
PortMatrixGrid _grid;
|
||||
|
||||
Arrangement _arrangement;
|
||||
uint32_t _alloc_width; ///< allocated width
|
||||
uint32_t _alloc_height; ///< allocated height
|
||||
Gdk::Rectangle _column_labels_rect;
|
||||
|
|
@ -108,11 +87,6 @@ private:
|
|||
uint32_t _yoffset;
|
||||
bool _pointer_inside;
|
||||
|
||||
/// bundles to offer for columns
|
||||
PortGroupList _column_ports;
|
||||
/// bundles to offer for rows
|
||||
PortGroupList _row_ports;
|
||||
|
||||
PortMatrixNode _mouseover;
|
||||
|
||||
std::list<sigc::connection> _bundle_connections;
|
||||
|
|
|
|||
|
|
@ -23,8 +23,8 @@
|
|||
#include "port_matrix_column_labels.h"
|
||||
#include "port_matrix.h"
|
||||
|
||||
PortMatrixColumnLabels::PortMatrixColumnLabels (PortMatrixBody* b, Location l)
|
||||
: PortMatrixComponent (b), _location (l)
|
||||
PortMatrixColumnLabels::PortMatrixColumnLabels (PortMatrix* m, PortMatrixBody* b)
|
||||
: PortMatrixComponent (m, b)
|
||||
{
|
||||
|
||||
}
|
||||
|
|
@ -45,7 +45,7 @@ PortMatrixColumnLabels::compute_dimensions ()
|
|||
/* width of the whole thing */
|
||||
_width = 0;
|
||||
|
||||
ARDOUR::BundleList const c = _body->column_ports().bundles();
|
||||
ARDOUR::BundleList const c = _matrix->columns()->bundles();
|
||||
for (ARDOUR::BundleList::const_iterator i = c.begin (); i != c.end(); ++i) {
|
||||
|
||||
cairo_text_extents_t ext;
|
||||
|
|
@ -77,7 +77,7 @@ PortMatrixColumnLabels::compute_dimensions ()
|
|||
}
|
||||
|
||||
_highest_group_name = 0;
|
||||
for (PortGroupList::const_iterator i = _body->column_ports().begin(); i != _body->column_ports().end(); ++i) {
|
||||
for (PortGroupList::List::const_iterator i = _matrix->columns()->begin(); i != _matrix->columns()->end(); ++i) {
|
||||
if ((*i)->visible()) {
|
||||
cairo_text_extents_t ext;
|
||||
cairo_text_extents (cr, (*i)->name.c_str(), &ext);
|
||||
|
|
@ -122,7 +122,7 @@ PortMatrixColumnLabels::render (cairo_t* cr)
|
|||
double x = 0;
|
||||
double y = 0;
|
||||
|
||||
if (_location == TOP) {
|
||||
if (_matrix->arrangement() == PortMatrix::TOP_TO_RIGHT) {
|
||||
x = slanted_height() / tan (angle());
|
||||
y = _highest_group_name + name_pad();
|
||||
} else {
|
||||
|
|
@ -131,7 +131,7 @@ PortMatrixColumnLabels::render (cairo_t* cr)
|
|||
}
|
||||
|
||||
int g = 0;
|
||||
for (PortGroupList::const_iterator i = _body->column_ports().begin(); i != _body->column_ports().end(); ++i) {
|
||||
for (PortGroupList::List::const_iterator i = _matrix->columns()->begin(); i != _matrix->columns()->end(); ++i) {
|
||||
|
||||
if (!(*i)->visible() || ((*i)->bundles().empty() && (*i)->ports.empty()) ) {
|
||||
continue;
|
||||
|
|
@ -147,9 +147,9 @@ PortMatrixColumnLabels::render (cairo_t* cr)
|
|||
/* rectangle */
|
||||
set_source_rgb (cr, get_a_group_colour (g));
|
||||
double const rh = _highest_group_name + 2 * name_pad();
|
||||
if (_location == TOP) {
|
||||
if (_matrix->arrangement() == PortMatrix::TOP_TO_RIGHT) {
|
||||
cairo_rectangle (cr, x, 0, w, rh);
|
||||
} else if (_location == BOTTOM) {
|
||||
} else {
|
||||
cairo_rectangle (cr, x, _height - rh, w, rh);
|
||||
}
|
||||
cairo_fill (cr);
|
||||
|
|
@ -168,7 +168,7 @@ PortMatrixColumnLabels::render (cairo_t* cr)
|
|||
/* BUNDLE PARALLELOGRAM-TYPE-THING AND NAME */
|
||||
|
||||
x = 0;
|
||||
ARDOUR::BundleList const c = _body->column_ports().bundles();
|
||||
ARDOUR::BundleList const c = _matrix->columns()->bundles();
|
||||
for (ARDOUR::BundleList::const_iterator i = c.begin (); i != c.end(); ++i) {
|
||||
|
||||
Gdk::Color colour = get_a_bundle_colour (i - c.begin ());
|
||||
|
|
@ -178,9 +178,9 @@ PortMatrixColumnLabels::render (cairo_t* cr)
|
|||
|
||||
double x_ = x;
|
||||
|
||||
if (_location == TOP) {
|
||||
if (_matrix->arrangement() == PortMatrix::TOP_TO_RIGHT) {
|
||||
y = _height;
|
||||
} else if (_location == BOTTOM) {
|
||||
} else {
|
||||
y = slanted_height();
|
||||
}
|
||||
|
||||
|
|
@ -201,7 +201,7 @@ PortMatrixColumnLabels::render (cairo_t* cr)
|
|||
|
||||
set_source_rgb (cr, text_colour());
|
||||
|
||||
if (_location == TOP) {
|
||||
if (_matrix->arrangement() == PortMatrix::TOP_TO_RIGHT) {
|
||||
|
||||
double const rl = 3 * name_pad() + _longest_channel_name;
|
||||
cairo_move_to (
|
||||
|
|
@ -210,7 +210,7 @@ PortMatrixColumnLabels::render (cairo_t* cr)
|
|||
_height - rl * sin (angle())
|
||||
);
|
||||
|
||||
} else if (_location == BOTTOM) {
|
||||
} else {
|
||||
|
||||
cairo_move_to (
|
||||
cr,
|
||||
|
|
@ -235,7 +235,7 @@ PortMatrixColumnLabels::render (cairo_t* cr)
|
|||
|
||||
for (uint32_t j = 0; j < (*i)->nchannels(); ++j) {
|
||||
|
||||
render_port_name (cr, get_a_bundle_colour (i - c.begin()), x, 0, PortMatrixBundleChannel (*i, j));
|
||||
render_port_name (cr, get_a_bundle_colour (i - c.begin()), x, 0, ARDOUR::BundleChannel (*i, j));
|
||||
x += column_width();
|
||||
}
|
||||
}
|
||||
|
|
@ -286,45 +286,57 @@ PortMatrixColumnLabels::draw_extra (cairo_t* cr)
|
|||
}
|
||||
}
|
||||
|
||||
void
|
||||
PortMatrixColumnLabels::render_port_name (cairo_t* cr, Gdk::Color colour, double xoff, double yoff, PortMatrixBundleChannel const &bc)
|
||||
std::vector<std::pair<double, double> >
|
||||
PortMatrixColumnLabels::port_name_shape (double xoff, double yoff) const
|
||||
{
|
||||
std::vector<std::pair<double, double> > shape;
|
||||
|
||||
double const lc = _longest_channel_name + name_pad();
|
||||
double const w = column_width();
|
||||
|
||||
if (_location == BOTTOM) {
|
||||
if (_matrix->arrangement() == PortMatrix::LEFT_TO_BOTTOM) {
|
||||
|
||||
double x_ = xoff + slanted_height() / tan (angle()) + w;
|
||||
double const ix = x_;
|
||||
double y_ = yoff;
|
||||
cairo_move_to (cr, x_, y_);
|
||||
shape.push_back (std::make_pair (x_, y_));
|
||||
x_ -= w;
|
||||
cairo_line_to (cr, x_, y_);
|
||||
shape.push_back (std::make_pair (x_, y_));
|
||||
x_ -= lc * cos (angle());
|
||||
y_ += lc * sin (angle());
|
||||
cairo_line_to (cr, x_, y_);
|
||||
shape.push_back (std::make_pair (x_, y_));
|
||||
x_ += w * pow (sin (angle()), 2);
|
||||
y_ += w * sin (angle()) * cos (angle());
|
||||
cairo_line_to (cr, x_, y_);
|
||||
cairo_line_to (cr, ix, yoff);
|
||||
shape.push_back (std::make_pair (x_, y_));
|
||||
|
||||
} else if (_location == TOP) {
|
||||
} else {
|
||||
|
||||
double x_ = xoff;
|
||||
double y_ = yoff + _height;
|
||||
cairo_move_to (cr, x_, y_);
|
||||
shape.push_back (std::make_pair (x_, y_));
|
||||
x_ += w;
|
||||
cairo_line_to (cr, x_, y_);
|
||||
shape.push_back (std::make_pair (x_, y_));
|
||||
x_ += lc * cos (angle());
|
||||
y_ -= lc * sin (angle());
|
||||
cairo_line_to (cr, x_, y_);
|
||||
shape.push_back (std::make_pair (x_, y_));
|
||||
x_ -= column_width() * pow (sin (angle()), 2);
|
||||
y_ -= column_width() * sin (angle()) * cos (angle());
|
||||
cairo_line_to (cr, x_, y_);
|
||||
cairo_line_to (cr, xoff, yoff + _height);
|
||||
|
||||
shape.push_back (std::make_pair (x_, y_));
|
||||
}
|
||||
|
||||
return shape;
|
||||
}
|
||||
|
||||
void
|
||||
PortMatrixColumnLabels::render_port_name (cairo_t* cr, Gdk::Color colour, double xoff, double yoff, ARDOUR::BundleChannel const &bc)
|
||||
{
|
||||
std::vector<std::pair<double, double> > const shape = port_name_shape (xoff, yoff);
|
||||
|
||||
cairo_move_to (cr, shape[0].first, shape[0].second);
|
||||
for (uint32_t i = 1; i < 4; ++i) {
|
||||
cairo_line_to (cr, shape[i].first, shape[i].second);
|
||||
}
|
||||
cairo_line_to (cr, shape[0].first, shape[0].second);
|
||||
|
||||
set_source_rgb (cr, colour);
|
||||
cairo_fill_preserve (cr);
|
||||
set_source_rgb (cr, background_colour());
|
||||
|
|
@ -333,7 +345,7 @@ PortMatrixColumnLabels::render_port_name (cairo_t* cr, Gdk::Color colour, double
|
|||
|
||||
set_source_rgb (cr, text_colour());
|
||||
|
||||
if (_location == TOP) {
|
||||
if (_matrix->arrangement() == PortMatrix::TOP_TO_RIGHT) {
|
||||
|
||||
cairo_move_to (
|
||||
cr,
|
||||
|
|
@ -341,7 +353,7 @@ PortMatrixColumnLabels::render_port_name (cairo_t* cr, Gdk::Color colour, double
|
|||
yoff + _height - name_pad() * sin (angle())
|
||||
);
|
||||
|
||||
} else if (_location == BOTTOM) {
|
||||
} else {
|
||||
|
||||
double const rl = 3 * name_pad() + _longest_bundle_name;
|
||||
cairo_move_to (
|
||||
|
|
@ -363,9 +375,18 @@ PortMatrixColumnLabels::render_port_name (cairo_t* cr, Gdk::Color colour, double
|
|||
}
|
||||
|
||||
double
|
||||
PortMatrixColumnLabels::channel_x (PortMatrixBundleChannel const &bc) const
|
||||
PortMatrixColumnLabels::channel_x (ARDOUR::BundleChannel const &bc) const
|
||||
{
|
||||
return bc.nchannels (_body->column_ports().bundles()) * column_width();
|
||||
uint32_t n = 0;
|
||||
|
||||
ARDOUR::BundleList::const_iterator i = _matrix->columns()->bundles().begin();
|
||||
while (i != _matrix->columns()->bundles().end() && *i != bc.bundle) {
|
||||
n += (*i)->nchannels ();
|
||||
++i;
|
||||
}
|
||||
|
||||
n += bc.channel;
|
||||
return n * column_width();
|
||||
}
|
||||
|
||||
void
|
||||
|
|
@ -376,7 +397,7 @@ PortMatrixColumnLabels::queue_draw_for (PortMatrixNode const& n)
|
|||
double const x = channel_x (n.column);
|
||||
double const lc = _longest_channel_name + name_pad();
|
||||
double const h = lc * sin (angle ()) + column_width() * sin (angle()) * cos (angle());
|
||||
if (_location == TOP) {
|
||||
if (_matrix->arrangement() == PortMatrix::TOP_TO_RIGHT) {
|
||||
|
||||
_body->queue_draw_area (
|
||||
component_to_parent_x (x),
|
||||
|
|
@ -385,7 +406,7 @@ PortMatrixColumnLabels::queue_draw_for (PortMatrixNode const& n)
|
|||
h
|
||||
);
|
||||
|
||||
} else if (_location == BOTTOM) {
|
||||
} else if (_matrix->arrangement() == PortMatrix::LEFT_TO_BOTTOM) {
|
||||
|
||||
double const x_ = x + slanted_height() / tan (angle()) - lc * cos (angle());
|
||||
|
||||
|
|
@ -401,3 +422,40 @@ PortMatrixColumnLabels::queue_draw_for (PortMatrixNode const& n)
|
|||
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
PortMatrixColumnLabels::button_press (double x, double y, int b, uint32_t t)
|
||||
{
|
||||
if (b != 3) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (!_matrix->can_rename_channels (_matrix->column_index()) &&
|
||||
!_matrix->can_remove_channels (_matrix->column_index())) {
|
||||
return;
|
||||
}
|
||||
|
||||
uint32_t N = _matrix->columns()->total_visible_ports ();
|
||||
uint32_t i = 0;
|
||||
for (; i < N; ++i) {
|
||||
|
||||
std::vector<std::pair<double, double> > const shape = port_name_shape (i * column_width(), 0);
|
||||
|
||||
uint32_t j = 0;
|
||||
for (; j < 4; ++j) {
|
||||
uint32_t k = (j + 1) % 4;
|
||||
|
||||
double const P = (y - shape[j].second) * (shape[k].first - shape[j].first) -
|
||||
(x - shape[j].first) * (shape[k].second - shape[j].second);
|
||||
|
||||
if (P > 0) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (j == 4) {
|
||||
_matrix->popup_channel_context_menu (_matrix->column_index(), i, t);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -25,22 +25,18 @@
|
|||
|
||||
namespace ARDOUR {
|
||||
class Bundle;
|
||||
class BundleChannel;
|
||||
}
|
||||
|
||||
class PortMatrixNode;
|
||||
class PortMatrixBundleChannel;
|
||||
|
||||
/** The column labels part of the port matrix */
|
||||
class PortMatrixColumnLabels : public PortMatrixComponent
|
||||
{
|
||||
public:
|
||||
PortMatrixColumnLabels (PortMatrix *, PortMatrixBody *);
|
||||
|
||||
enum Location {
|
||||
TOP,
|
||||
BOTTOM
|
||||
};
|
||||
|
||||
PortMatrixColumnLabels (PortMatrixBody *, Location);
|
||||
void button_press (double, double, int, uint32_t);
|
||||
|
||||
double component_to_parent_x (double x) const;
|
||||
double parent_to_component_x (double x) const;
|
||||
|
|
@ -53,9 +49,10 @@ private:
|
|||
void render (cairo_t *);
|
||||
void compute_dimensions ();
|
||||
double basic_text_x_pos (int) const;
|
||||
void render_port_name (cairo_t *, Gdk::Color, double, double, PortMatrixBundleChannel const &);
|
||||
double channel_x (PortMatrixBundleChannel const &) const;
|
||||
void render_port_name (cairo_t *, Gdk::Color, double, double, ARDOUR::BundleChannel const &);
|
||||
double channel_x (ARDOUR::BundleChannel const &) const;
|
||||
void queue_draw_for (PortMatrixNode const &);
|
||||
std::vector<std::pair<double, double> > port_name_shape (double, double) const;
|
||||
|
||||
double slanted_height () const {
|
||||
return _height - _highest_group_name - 2 * name_pad();
|
||||
|
|
@ -66,7 +63,6 @@ private:
|
|||
double _longest_channel_name;
|
||||
double _highest_text;
|
||||
double _highest_group_name;
|
||||
Location _location;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
|||
|
|
@ -23,8 +23,9 @@
|
|||
/** Constructor.
|
||||
* @param p Port matrix that we're in.
|
||||
*/
|
||||
PortMatrixComponent::PortMatrixComponent (PortMatrixBody* b)
|
||||
: _body (b),
|
||||
PortMatrixComponent::PortMatrixComponent (PortMatrix* m, PortMatrixBody* b)
|
||||
: _matrix (m),
|
||||
_body (b),
|
||||
_pixmap (0),
|
||||
_render_required (true),
|
||||
_dimension_computation_required (true)
|
||||
|
|
|
|||
|
|
@ -22,6 +22,7 @@
|
|||
|
||||
#include <gtkmm/eventbox.h>
|
||||
|
||||
class PortMatrix;
|
||||
class PortMatrixBody;
|
||||
class PortMatrixNode;
|
||||
|
||||
|
|
@ -31,7 +32,7 @@ class PortMatrixNode;
|
|||
class PortMatrixComponent
|
||||
{
|
||||
public:
|
||||
PortMatrixComponent (PortMatrixBody *);
|
||||
PortMatrixComponent (PortMatrix *, PortMatrixBody *);
|
||||
virtual ~PortMatrixComponent ();
|
||||
|
||||
virtual double component_to_parent_x (double x) const = 0;
|
||||
|
|
@ -174,6 +175,7 @@ protected:
|
|||
*/
|
||||
virtual void compute_dimensions () = 0;
|
||||
|
||||
PortMatrix* _matrix;
|
||||
PortMatrixBody* _body; ///< the PortMatrixBody that we're in
|
||||
uint32_t _width; ///< full width of the contents
|
||||
uint32_t _height; ///< full height of the contents
|
||||
|
|
|
|||
|
|
@ -24,9 +24,8 @@
|
|||
#include "port_matrix_grid.h"
|
||||
#include "port_matrix.h"
|
||||
|
||||
PortMatrixGrid::PortMatrixGrid (PortMatrix* p, PortMatrixBody* b)
|
||||
: PortMatrixComponent (b),
|
||||
_port_matrix (p)
|
||||
PortMatrixGrid::PortMatrixGrid (PortMatrix* m, PortMatrixBody* b)
|
||||
: PortMatrixComponent (m, b)
|
||||
{
|
||||
|
||||
}
|
||||
|
|
@ -35,13 +34,13 @@ void
|
|||
PortMatrixGrid::compute_dimensions ()
|
||||
{
|
||||
_width = 0;
|
||||
ARDOUR::BundleList const c = _body->column_ports().bundles();
|
||||
ARDOUR::BundleList const c = _matrix->columns()->bundles();
|
||||
for (ARDOUR::BundleList::const_iterator i = c.begin(); i != c.end(); ++i) {
|
||||
_width += (*i)->nchannels() * column_width();
|
||||
}
|
||||
|
||||
_height = 0;
|
||||
ARDOUR::BundleList const r = _body->row_ports().bundles();
|
||||
ARDOUR::BundleList const r = _matrix->rows()->bundles();
|
||||
for (ARDOUR::BundleList::const_iterator i = r.begin(); i != r.end(); ++i) {
|
||||
_height += (*i)->nchannels() * row_height();
|
||||
}
|
||||
|
|
@ -61,7 +60,7 @@ PortMatrixGrid::render (cairo_t* cr)
|
|||
|
||||
set_source_rgb (cr, grid_colour());
|
||||
uint32_t x = 0;
|
||||
ARDOUR::BundleList const c = _body->column_ports().bundles();
|
||||
ARDOUR::BundleList const c = _matrix->columns()->bundles();
|
||||
for (ARDOUR::BundleList::size_type i = 0; i < c.size(); ++i) {
|
||||
|
||||
cairo_set_line_width (cr, thin_grid_line_width());
|
||||
|
|
@ -86,7 +85,7 @@ PortMatrixGrid::render (cairo_t* cr)
|
|||
/* HORIZONTAL GRID LINES */
|
||||
|
||||
uint32_t y = 0;
|
||||
ARDOUR::BundleList const r = _body->row_ports().bundles();
|
||||
ARDOUR::BundleList const r = _matrix->rows()->bundles();
|
||||
for (ARDOUR::BundleList::size_type i = 0; i < r.size(); ++i) {
|
||||
|
||||
cairo_set_line_width (cr, thin_grid_line_width());
|
||||
|
|
@ -122,7 +121,11 @@ PortMatrixGrid::render (cairo_t* cr)
|
|||
y = by;
|
||||
for (uint32_t l = 0; l < (*j)->nchannels (); ++l) {
|
||||
|
||||
PortMatrix::State const s = _port_matrix->get_state (*j, l, *i, k);
|
||||
ARDOUR::BundleChannel c[2];
|
||||
c[_matrix->column_index()] = ARDOUR::BundleChannel (*i, k);
|
||||
c[_matrix->row_index()] = ARDOUR::BundleChannel (*j, l);
|
||||
|
||||
PortMatrix::State const s = _matrix->get_state (c);
|
||||
|
||||
switch (s) {
|
||||
case PortMatrix::ASSOCIATED:
|
||||
|
|
@ -172,32 +175,32 @@ PortMatrixNode
|
|||
PortMatrixGrid::position_to_node (double x, double y) const
|
||||
{
|
||||
return PortMatrixNode (
|
||||
position_to_channel (y, _body->row_ports().bundles(), row_height()),
|
||||
position_to_channel (x, _body->column_ports().bundles(), column_width())
|
||||
position_to_channel (y, _matrix->rows()->bundles(), row_height()),
|
||||
position_to_channel (x, _matrix->columns()->bundles(), column_width())
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
PortMatrixBundleChannel
|
||||
ARDOUR::BundleChannel
|
||||
PortMatrixGrid::position_to_channel (double p, ARDOUR::BundleList const& bundles, double inc) const
|
||||
{
|
||||
uint32_t pos = p / inc;
|
||||
|
||||
for (ARDOUR::BundleList::const_iterator i = bundles.begin(); i != bundles.end(); ++i) {
|
||||
if (pos < (*i)->nchannels()) {
|
||||
return PortMatrixBundleChannel (*i, pos);
|
||||
return ARDOUR::BundleChannel (*i, pos);
|
||||
} else {
|
||||
pos -= (*i)->nchannels();
|
||||
}
|
||||
}
|
||||
|
||||
return PortMatrixBundleChannel (boost::shared_ptr<ARDOUR::Bundle> (), 0);
|
||||
return ARDOUR::BundleChannel (boost::shared_ptr<ARDOUR::Bundle> (), 0);
|
||||
}
|
||||
|
||||
|
||||
double
|
||||
PortMatrixGrid::channel_position (
|
||||
PortMatrixBundleChannel bc,
|
||||
ARDOUR::BundleChannel bc,
|
||||
ARDOUR::BundleList const& bundles,
|
||||
double inc) const
|
||||
{
|
||||
|
|
@ -225,20 +228,21 @@ PortMatrixGrid::button_press (double x, double y, int b)
|
|||
|
||||
if (node.row.bundle && node.column.bundle) {
|
||||
|
||||
PortMatrix::State const s = _port_matrix->get_state (
|
||||
node.row.bundle, node.row.channel, node.column.bundle, node.column.channel
|
||||
);
|
||||
ARDOUR::BundleChannel c[2];
|
||||
c[_matrix->row_index()] = node.row;
|
||||
c[_matrix->column_index()] = node.column;
|
||||
|
||||
PortMatrix::State const s = _matrix->get_state (c);
|
||||
|
||||
if (s == PortMatrix::ASSOCIATED || s == PortMatrix::NOT_ASSOCIATED) {
|
||||
|
||||
bool const n = !(s == PortMatrix::ASSOCIATED);
|
||||
|
||||
_port_matrix->set_state (
|
||||
node.row.bundle, node.row.channel,
|
||||
node.column.bundle, node.column.channel,
|
||||
n, 0
|
||||
);
|
||||
ARDOUR::BundleChannel c[2];
|
||||
c[_matrix->row_index()] = node.row;
|
||||
c[_matrix->column_index()] = node.column;
|
||||
|
||||
_matrix->set_state (c, n);
|
||||
}
|
||||
|
||||
require_render ();
|
||||
|
|
@ -253,19 +257,19 @@ PortMatrixGrid::draw_extra (cairo_t* cr)
|
|||
cairo_set_line_width (cr, mouseover_line_width());
|
||||
|
||||
double const x = component_to_parent_x (
|
||||
channel_position (_body->mouseover().column, _body->column_ports().bundles(), column_width()) + column_width() / 2
|
||||
channel_position (_body->mouseover().column, _matrix->columns()->bundles(), column_width()) + column_width() / 2
|
||||
);
|
||||
|
||||
double const y = component_to_parent_y (
|
||||
channel_position (_body->mouseover().row, _body->row_ports().bundles(), row_height()) + row_height() / 2
|
||||
channel_position (_body->mouseover().row, _matrix->rows()->bundles(), row_height()) + row_height() / 2
|
||||
);
|
||||
|
||||
if (_body->mouseover().row.bundle) {
|
||||
|
||||
cairo_move_to (cr, x, y);
|
||||
if (_body->arrangement() == PortMatrixBody::BOTTOM_AND_LEFT) {
|
||||
if (_matrix->arrangement() == PortMatrix::LEFT_TO_BOTTOM) {
|
||||
cairo_line_to (cr, component_to_parent_x (0), y);
|
||||
} else if (_body->arrangement() == PortMatrixBody::TOP_AND_RIGHT) {
|
||||
} else if (_matrix->arrangement() == PortMatrix::TOP_TO_RIGHT) {
|
||||
cairo_line_to (cr, _parent_rectangle.get_x() + _parent_rectangle.get_width(), y);
|
||||
}
|
||||
cairo_stroke (cr);
|
||||
|
|
@ -274,9 +278,9 @@ PortMatrixGrid::draw_extra (cairo_t* cr)
|
|||
if (_body->mouseover().column.bundle) {
|
||||
|
||||
cairo_move_to (cr, x, y);
|
||||
if (_body->arrangement() == PortMatrixBody::BOTTOM_AND_LEFT) {
|
||||
if (_matrix->arrangement() == PortMatrix::LEFT_TO_BOTTOM) {
|
||||
cairo_line_to (cr, x, _parent_rectangle.get_y() + _parent_rectangle.get_height());
|
||||
} else if (_body->arrangement() == PortMatrixBody::TOP_AND_RIGHT) {
|
||||
} else if (_matrix->arrangement() == PortMatrix::TOP_TO_RIGHT) {
|
||||
cairo_line_to (cr, x, component_to_parent_y (0));
|
||||
}
|
||||
cairo_stroke (cr);
|
||||
|
|
@ -301,7 +305,7 @@ PortMatrixGrid::queue_draw_for (PortMatrixNode const &n)
|
|||
{
|
||||
if (n.row.bundle) {
|
||||
|
||||
double const y = channel_position (n.row, _body->row_ports().bundles(), row_height());
|
||||
double const y = channel_position (n.row, _matrix->rows()->bundles(), row_height());
|
||||
_body->queue_draw_area (
|
||||
_parent_rectangle.get_x(),
|
||||
component_to_parent_y (y),
|
||||
|
|
@ -312,7 +316,7 @@ PortMatrixGrid::queue_draw_for (PortMatrixNode const &n)
|
|||
|
||||
if (n.column.bundle) {
|
||||
|
||||
double const x = channel_position (n.column, _body->column_ports().bundles(), column_width());
|
||||
double const x = channel_position (n.column, _matrix->columns()->bundles(), column_width());
|
||||
|
||||
_body->queue_draw_area (
|
||||
component_to_parent_x (x),
|
||||
|
|
|
|||
|
|
@ -34,7 +34,7 @@ namespace ARDOUR {
|
|||
class Bundle;
|
||||
}
|
||||
|
||||
/// The grid part of the port matrix
|
||||
/** The grid part of the port matrix */
|
||||
class PortMatrixGrid : public PortMatrixComponent
|
||||
{
|
||||
public:
|
||||
|
|
@ -55,12 +55,10 @@ private:
|
|||
void compute_dimensions ();
|
||||
void render (cairo_t *);
|
||||
|
||||
double channel_position (PortMatrixBundleChannel, ARDOUR::BundleList const &, double) const;
|
||||
double channel_position (ARDOUR::BundleChannel, ARDOUR::BundleList const &, double) const;
|
||||
PortMatrixNode position_to_node (double, double) const;
|
||||
PortMatrixBundleChannel position_to_channel (double, ARDOUR::BundleList const &, double) const;
|
||||
ARDOUR::BundleChannel position_to_channel (double, ARDOUR::BundleList const &, double) const;
|
||||
void queue_draw_for (PortMatrixNode const &);
|
||||
|
||||
PortMatrix* _port_matrix;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
|||
|
|
@ -19,26 +19,18 @@
|
|||
|
||||
#include <iostream>
|
||||
#include <boost/weak_ptr.hpp>
|
||||
#include <gtkmm/menu.h>
|
||||
#include <gtkmm/menushell.h>
|
||||
#include <gtkmm/menu_elems.h>
|
||||
#include <cairo/cairo.h>
|
||||
#include "ardour/bundle.h"
|
||||
#include "port_matrix_row_labels.h"
|
||||
#include "port_matrix.h"
|
||||
#include "i18n.h"
|
||||
|
||||
PortMatrixRowLabels::PortMatrixRowLabels (PortMatrix* p, PortMatrixBody* b, Location l)
|
||||
: PortMatrixComponent (b), _port_matrix (p), _menu (0), _location (l)
|
||||
PortMatrixRowLabels::PortMatrixRowLabels (PortMatrix* m, PortMatrixBody* b)
|
||||
: PortMatrixComponent (m, b)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
PortMatrixRowLabels::~PortMatrixRowLabels ()
|
||||
{
|
||||
delete _menu;
|
||||
}
|
||||
|
||||
void
|
||||
PortMatrixRowLabels::compute_dimensions ()
|
||||
{
|
||||
|
|
@ -49,7 +41,7 @@ PortMatrixRowLabels::compute_dimensions ()
|
|||
_longest_port_name = 0;
|
||||
_longest_bundle_name = 0;
|
||||
_height = 0;
|
||||
ARDOUR::BundleList const r = _body->row_ports().bundles();
|
||||
ARDOUR::BundleList const r = _matrix->rows()->bundles();
|
||||
for (ARDOUR::BundleList::const_iterator i = r.begin(); i != r.end(); ++i) {
|
||||
for (uint32_t j = 0; j < (*i)->nchannels(); ++j) {
|
||||
cairo_text_extents_t ext;
|
||||
|
|
@ -69,7 +61,7 @@ PortMatrixRowLabels::compute_dimensions ()
|
|||
}
|
||||
|
||||
_highest_group_name = 0;
|
||||
for (PortGroupList::const_iterator i = _body->row_ports().begin(); i != _body->row_ports().end(); ++i) {
|
||||
for (PortGroupList::List::const_iterator i = _matrix->rows()->begin(); i != _matrix->rows()->end(); ++i) {
|
||||
if ((*i)->visible()) {
|
||||
cairo_text_extents_t ext;
|
||||
cairo_text_extents (cr, (*i)->name.c_str(), &ext);
|
||||
|
|
@ -101,15 +93,15 @@ PortMatrixRowLabels::render (cairo_t* cr)
|
|||
/* PORT GROUP NAMES */
|
||||
|
||||
double x = 0;
|
||||
if (_location == LEFT) {
|
||||
if (_matrix->arrangement() == PortMatrix::LEFT_TO_BOTTOM) {
|
||||
x = 0;
|
||||
} else if (_location == RIGHT) {
|
||||
} else {
|
||||
x = _width - _highest_group_name - 2 * name_pad();
|
||||
}
|
||||
|
||||
double y = 0;
|
||||
int g = 0;
|
||||
for (PortGroupList::const_iterator i = _body->row_ports().begin(); i != _body->row_ports().end(); ++i) {
|
||||
for (PortGroupList::List::const_iterator i = _matrix->rows()->begin(); i != _matrix->rows()->end(); ++i) {
|
||||
|
||||
if (!(*i)->visible() || ((*i)->bundles().empty() && (*i)->ports.empty()) ) {
|
||||
continue;
|
||||
|
|
@ -146,14 +138,14 @@ PortMatrixRowLabels::render (cairo_t* cr)
|
|||
/* BUNDLE NAMES */
|
||||
|
||||
x = 0;
|
||||
if (_location == LEFT) {
|
||||
if (_matrix->arrangement() == PortMatrix::LEFT_TO_BOTTOM) {
|
||||
x = _highest_group_name + 2 * name_pad();
|
||||
} else if (_location == RIGHT) {
|
||||
} else {
|
||||
x = _longest_port_name + name_pad() * 2;
|
||||
}
|
||||
|
||||
y = 0;
|
||||
ARDOUR::BundleList const r = _body->row_ports().bundles();
|
||||
ARDOUR::BundleList const r = _matrix->rows()->bundles();
|
||||
for (ARDOUR::BundleList::const_iterator i = r.begin(); i != r.end(); ++i) {
|
||||
|
||||
Gdk::Color const colour = get_a_bundle_colour (i - r.begin ());
|
||||
|
|
@ -187,7 +179,7 @@ PortMatrixRowLabels::render (cairo_t* cr)
|
|||
y = 0;
|
||||
for (ARDOUR::BundleList::const_iterator i = r.begin(); i != r.end(); ++i) {
|
||||
for (uint32_t j = 0; j < (*i)->nchannels(); ++j) {
|
||||
render_port_name (cr, get_a_bundle_colour (i - r.begin()), 0, y, PortMatrixBundleChannel (*i, j));
|
||||
render_port_name (cr, get_a_bundle_colour (i - r.begin()), 0, y, ARDOUR::BundleChannel (*i, j));
|
||||
y += row_height();
|
||||
}
|
||||
}
|
||||
|
|
@ -200,84 +192,20 @@ PortMatrixRowLabels::button_press (double x, double y, int b, uint32_t t)
|
|||
return;
|
||||
}
|
||||
|
||||
if ( (_location == LEFT && x > (_longest_bundle_name + name_pad() * 2)) ||
|
||||
(_location == RIGHT && x < (_longest_port_name + name_pad() * 2))
|
||||
if (!_matrix->can_rename_channels (_matrix->row_index()) &&
|
||||
!_matrix->can_remove_channels (_matrix->row_index())) {
|
||||
return;
|
||||
}
|
||||
|
||||
if ( (_matrix->arrangement() == PortMatrix::LEFT_TO_BOTTOM && x > (_longest_bundle_name + name_pad() * 2)) ||
|
||||
(_matrix->arrangement() == PortMatrix::TOP_TO_RIGHT && x < (_longest_port_name + name_pad() * 2))
|
||||
) {
|
||||
|
||||
delete _menu;
|
||||
_matrix->popup_channel_context_menu (_matrix->row_index(), y / row_height(), t);
|
||||
|
||||
_menu = new Gtk::Menu;
|
||||
_menu->set_name ("ArdourContextMenu");
|
||||
|
||||
Gtk::Menu_Helpers::MenuList& items = _menu->items ();
|
||||
|
||||
uint32_t row = y / row_height ();
|
||||
|
||||
boost::shared_ptr<ARDOUR::Bundle> bundle;
|
||||
uint32_t channel = 0;
|
||||
|
||||
ARDOUR::BundleList const r = _body->row_ports().bundles();
|
||||
for (ARDOUR::BundleList::const_iterator i = r.begin(); i != r.end(); ++i) {
|
||||
if (row < (*i)->nchannels ()) {
|
||||
bundle = *i;
|
||||
channel = row;
|
||||
break;
|
||||
} else {
|
||||
row -= (*i)->nchannels ();
|
||||
}
|
||||
}
|
||||
|
||||
if (bundle) {
|
||||
char buf [64];
|
||||
|
||||
if (_port_matrix->can_rename_channels ()) {
|
||||
snprintf (buf, sizeof (buf), _("Rename '%s'..."), bundle->channel_name (channel).c_str());
|
||||
items.push_back (
|
||||
Gtk::Menu_Helpers::MenuElem (
|
||||
buf,
|
||||
sigc::bind (sigc::mem_fun (*this, &PortMatrixRowLabels::rename_channel_proxy), bundle, channel)
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
snprintf (buf, sizeof (buf), _("Remove '%s'"), bundle->channel_name (channel).c_str());
|
||||
items.push_back (
|
||||
Gtk::Menu_Helpers::MenuElem (
|
||||
buf,
|
||||
sigc::bind (sigc::mem_fun (*this, &PortMatrixRowLabels::remove_channel_proxy), bundle, channel)
|
||||
)
|
||||
);
|
||||
|
||||
_menu->popup (1, t);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
PortMatrixRowLabels::remove_channel_proxy (boost::weak_ptr<ARDOUR::Bundle> b, uint32_t c)
|
||||
{
|
||||
boost::shared_ptr<ARDOUR::Bundle> sb = b.lock ();
|
||||
if (!sb) {
|
||||
return;
|
||||
}
|
||||
|
||||
_port_matrix->remove_channel (sb, c);
|
||||
|
||||
}
|
||||
|
||||
void
|
||||
PortMatrixRowLabels::rename_channel_proxy (boost::weak_ptr<ARDOUR::Bundle> b, uint32_t c)
|
||||
{
|
||||
boost::shared_ptr<ARDOUR::Bundle> sb = b.lock ();
|
||||
if (!sb) {
|
||||
return;
|
||||
}
|
||||
|
||||
_port_matrix->rename_channel (sb, c);
|
||||
}
|
||||
|
||||
|
||||
double
|
||||
PortMatrixRowLabels::component_to_parent_x (double x) const
|
||||
{
|
||||
|
|
@ -305,9 +233,9 @@ PortMatrixRowLabels::parent_to_component_y (double y) const
|
|||
double
|
||||
PortMatrixRowLabels::port_name_x () const
|
||||
{
|
||||
if (_location == LEFT) {
|
||||
if (_matrix->arrangement() == PortMatrix::LEFT_TO_BOTTOM) {
|
||||
return _longest_bundle_name + _highest_group_name + name_pad() * 4;
|
||||
} else if (_location == RIGHT) {
|
||||
} else {
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
@ -316,7 +244,7 @@ PortMatrixRowLabels::port_name_x () const
|
|||
|
||||
void
|
||||
PortMatrixRowLabels::render_port_name (
|
||||
cairo_t* cr, Gdk::Color colour, double xoff, double yoff, PortMatrixBundleChannel const& bc
|
||||
cairo_t* cr, Gdk::Color colour, double xoff, double yoff, ARDOUR::BundleChannel const& bc
|
||||
)
|
||||
{
|
||||
set_source_rgb (cr, colour);
|
||||
|
|
@ -336,9 +264,18 @@ PortMatrixRowLabels::render_port_name (
|
|||
}
|
||||
|
||||
double
|
||||
PortMatrixRowLabels::channel_y (PortMatrixBundleChannel const& bc) const
|
||||
PortMatrixRowLabels::channel_y (ARDOUR::BundleChannel const& bc) const
|
||||
{
|
||||
return bc.nchannels (_body->row_ports().bundles()) * row_height();
|
||||
uint32_t n = 0;
|
||||
|
||||
ARDOUR::BundleList::const_iterator i = _matrix->rows()->bundles().begin();
|
||||
while (i != _matrix->rows()->bundles().end() && *i != bc.bundle) {
|
||||
n += (*i)->nchannels ();
|
||||
++i;
|
||||
}
|
||||
|
||||
n += bc.channel;
|
||||
return n * row_height();
|
||||
}
|
||||
|
||||
void
|
||||
|
|
|
|||
|
|
@ -27,26 +27,21 @@
|
|||
class PortMatrix;
|
||||
class PortMatrixBody;
|
||||
class PortMatrixNode;
|
||||
class PortMatrixBundleChannel;
|
||||
|
||||
namespace ARDOUR {
|
||||
class Bundle;
|
||||
class BundleChannel;
|
||||
}
|
||||
|
||||
namespace Gtk {
|
||||
class Menu;
|
||||
}
|
||||
|
||||
/** The row labels part of the port matrix */
|
||||
class PortMatrixRowLabels : public PortMatrixComponent
|
||||
{
|
||||
public:
|
||||
enum Location {
|
||||
LEFT,
|
||||
RIGHT
|
||||
};
|
||||
|
||||
PortMatrixRowLabels (PortMatrix *, PortMatrixBody *, Location);
|
||||
~PortMatrixRowLabels ();
|
||||
PortMatrixRowLabels (PortMatrix *, PortMatrixBody *);
|
||||
|
||||
void button_press (double, double, int, uint32_t);
|
||||
|
||||
|
|
@ -62,17 +57,14 @@ private:
|
|||
void compute_dimensions ();
|
||||
void remove_channel_proxy (boost::weak_ptr<ARDOUR::Bundle>, uint32_t);
|
||||
void rename_channel_proxy (boost::weak_ptr<ARDOUR::Bundle>, uint32_t);
|
||||
void render_port_name (cairo_t *, Gdk::Color, double, double, PortMatrixBundleChannel const &);
|
||||
double channel_y (PortMatrixBundleChannel const &) const;
|
||||
void render_port_name (cairo_t *, Gdk::Color, double, double, ARDOUR::BundleChannel const &);
|
||||
double channel_y (ARDOUR::BundleChannel const &) const;
|
||||
void queue_draw_for (PortMatrixNode const &);
|
||||
double port_name_x () const;
|
||||
|
||||
PortMatrix* _port_matrix;
|
||||
double _longest_port_name;
|
||||
double _longest_bundle_name;
|
||||
double _highest_group_name;
|
||||
Gtk::Menu* _menu;
|
||||
Location _location;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
|||
|
|
@ -22,36 +22,10 @@
|
|||
|
||||
#include "ardour/bundle.h"
|
||||
|
||||
struct PortMatrixBundleChannel {
|
||||
PortMatrixBundleChannel () : channel (0) {}
|
||||
PortMatrixBundleChannel (boost::shared_ptr<ARDOUR::Bundle> b, uint32_t c)
|
||||
: bundle (b), channel (c) {}
|
||||
|
||||
bool operator== (PortMatrixBundleChannel const& other) const {
|
||||
return bundle == other.bundle && channel == other.channel;
|
||||
}
|
||||
bool operator!= (PortMatrixBundleChannel const& other) const {
|
||||
return bundle != other.bundle || channel != other.channel;
|
||||
}
|
||||
|
||||
uint32_t nchannels (ARDOUR::BundleList const& bl) const {
|
||||
uint32_t n = 0;
|
||||
ARDOUR::BundleList::const_iterator i = bl.begin();
|
||||
while (i != bl.end() && *i != bundle) {
|
||||
n += (*i)->nchannels ();
|
||||
++i;
|
||||
}
|
||||
n += channel;
|
||||
return n;
|
||||
}
|
||||
|
||||
boost::shared_ptr<ARDOUR::Bundle> bundle;
|
||||
uint32_t channel;
|
||||
};
|
||||
|
||||
struct PortMatrixNode {
|
||||
struct PortMatrixNode
|
||||
{
|
||||
PortMatrixNode () {}
|
||||
PortMatrixNode (PortMatrixBundleChannel r, PortMatrixBundleChannel c) : row (r), column (c) {}
|
||||
PortMatrixNode (ARDOUR::BundleChannel r, ARDOUR::BundleChannel c) : row (r), column (c) {}
|
||||
|
||||
bool operator== (PortMatrixNode const& other) const {
|
||||
return row == other.row && column == other.column;
|
||||
|
|
@ -60,8 +34,8 @@ struct PortMatrixNode {
|
|||
return row != other.row || column != other.column;
|
||||
}
|
||||
|
||||
PortMatrixBundleChannel row;
|
||||
PortMatrixBundleChannel column;
|
||||
ARDOUR::BundleChannel row;
|
||||
ARDOUR::BundleChannel column;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
|||
|
|
@ -147,6 +147,30 @@ class Bundle : public sigc::trackable
|
|||
bool _ports_are_inputs;
|
||||
};
|
||||
|
||||
|
||||
|
||||
struct BundleChannel
|
||||
{
|
||||
BundleChannel () : channel (0) {}
|
||||
|
||||
BundleChannel (boost::shared_ptr<ARDOUR::Bundle> b, uint32_t c)
|
||||
: bundle (b), channel (c) {}
|
||||
|
||||
bool operator== (BundleChannel const& other) const {
|
||||
return bundle == other.bundle && channel == other.channel;
|
||||
}
|
||||
|
||||
bool operator!= (BundleChannel const& other) const {
|
||||
return bundle != other.bundle || channel != other.channel;
|
||||
}
|
||||
|
||||
boost::shared_ptr<ARDOUR::Bundle> bundle;
|
||||
uint32_t channel;
|
||||
};
|
||||
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
||||
#endif /* __ardour_bundle_h__ */
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue