2 * Copyright (C) 2016-2017 Paul Davis <paul@linuxaudiosystems.com>
3 * Copyright (C) 2016-2017 Robin Gareus <robin@gareus.org>
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or
8 * (at your option) any later version.
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
15 * You should have received a copy of the GNU General Public License along
16 * with this program; if not, write to the Free Software Foundation, Inc.,
17 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
20 #include "evoral/ControlList.hpp"
22 #include "ardour/mute_master.h"
23 #include "ardour/session.h"
24 #include "ardour/mute_control.h"
28 using namespace ARDOUR;
32 MuteControl::MuteControl (Session& session, std::string const & name, Muteable& m)
33 : SlavableAutomationControl (session, MuteAutomation, ParameterDescriptor (MuteAutomation),
34 boost::shared_ptr<AutomationList> (new AutomationList (Evoral::Parameter (MuteAutomation))),
38 _list->set_interpolation (Evoral::ControlList::Discrete);
39 /* mute changes must be synchronized by the process cycle */
40 set_flags (Controllable::Flag (flags() | Controllable::RealTime));
44 MuteControl::post_add_master (boost::shared_ptr<AutomationControl> m)
48 /* boolean masters records are not updated until AFTER
49 * ::post_add_master() is called, so we can use them to check
50 * on whether any master was already enabled before the new
54 if (!muted_by_self() && !get_boolean_masters()) {
55 _muteable.mute_master()->set_muted_by_masters (true);
56 Changed (false, Controllable::NoGroup); /* EMIT SIGNAL */
62 MuteControl::pre_remove_master (boost::shared_ptr<AutomationControl> m)
65 /* null control ptr means we're removing all masters */
66 _muteable.mute_master()->set_muted_by_masters (false);
67 /* Changed will be emitted in SlavableAutomationControl::clear_masters() */
71 if (m->get_value() && get_boolean_masters() == 1) {
72 _muteable.mute_master()->set_muted_by_masters (false);
73 if (!muted_by_self()) {
74 Changed (false, Controllable::NoGroup); /* EMIT SIGNAL */
80 MuteControl::actually_set_value (double val, Controllable::GroupControlDisposition gcd)
82 if (muted_by_self() != bool (val)) {
83 _muteable.mute_master()->set_muted_by_self (val);
85 /* allow the Muteable to respond to the mute change
86 before anybody else knows about it.
88 _muteable.act_on_mute ();
91 SlavableAutomationControl::actually_set_value (val, gcd);
95 MuteControl::handle_master_change (boost::shared_ptr<AutomationControl> m)
97 bool send_signal = false;
98 boost::shared_ptr<MuteControl> mc = boost::dynamic_pointer_cast<MuteControl> (m);
103 if (m->get_value()) {
104 /* this master is now enabled */
105 if (get_boolean_masters() == 0) {
106 _muteable.mute_master()->set_muted_by_masters (true);
107 if (!muted_by_self()) {
112 /* this master is disabled and there was only 1 enabled before */
113 if (get_boolean_masters() == 1) {
114 _muteable.mute_master()->set_muted_by_masters (false);
115 if (!muted_by_self()) {
124 MuteControl::get_value () const
127 return muted_by_self() || muted_by_masters ();
130 if (_list && boost::dynamic_pointer_cast<AutomationList>(_list)->automation_playback()) {
131 // Playing back automation, get the value from the list
132 return AutomationControl::get_value();
139 MuteControl::set_mute_points (MuteMaster::MutePoint mp)
141 _muteable.mute_master()->set_mute_points (mp);
142 _muteable.mute_points_changed (); /* EMIT SIGNAL */
144 if (_muteable.mute_master()->muted_by_self()) {
145 Changed (true, Controllable::UseGroup); /* EMIT SIGNAL */
149 MuteMaster::MutePoint
150 MuteControl::mute_points () const
152 return _muteable.mute_master()->mute_points ();
156 MuteControl::muted () const
158 /* have to get (self-muted) value from somewhere. could be our own
159 Control, or the Muteable that we sort-of proxy for. Since this
160 method is called by ::get_value(), use the latter to avoid recursion.
162 return _muteable.mute_master()->muted_by_self() || muted_by_masters ();
166 MuteControl::muted_by_self () const
168 return _muteable.mute_master()->muted_by_self();
172 MuteControl::muted_by_masters () const
174 return _muteable.mute_master()->muted_by_masters ();
178 MuteControl::muted_by_others_soloing () const
180 return _muteable.muted_by_others_soloing ();
184 MuteControl::automation_run (samplepos_t start, pframes_t len)
186 boolean_automation_run (start, len);
191 if (list() && automation_playback()) {
192 mute = list()->rt_safe_eval (start, valid) >= 0.5;
199 if (muted_by_masters ()) {
200 /* already muted, no need to check further,
201 * except we need to up update implicit/explict mute
203 if (muted_by_self () != mute) {
204 set_value_unchecked (mute ? 1. : 0.);
205 Changed (false, Controllable::NoGroup); /* EMIT SIGNAL */
210 if (mute && !muted()) {
211 set_value_unchecked (1.0); // mute
212 Changed (false, Controllable::NoGroup); /* EMIT SIGNAL */
213 } else if (!mute && muted()) {
214 set_value_unchecked (0.0); // unmute
215 Changed (false, Controllable::NoGroup); /* EMIT SIGNAL */