Plugin: fix additive note resolution

When stopping transport in the middle of a note, each plugin
will resolve the note, resulting in multiple duplicate note-off
events.
This commit is contained in:
Robin Gareus 2023-06-30 16:32:27 +02:00
parent 71d45286f4
commit b51cf0ed95
No known key found for this signature in database
GPG key ID: A090BCE02CF57F04
2 changed files with 14 additions and 5 deletions

View file

@ -23,6 +23,7 @@
#ifndef __ardour_plugin_h__ #ifndef __ardour_plugin_h__
#define __ardour_plugin_h__ #define __ardour_plugin_h__
#include <atomic>
#include <memory> #include <memory>
#include <set> #include <set>
#include <string> #include <string>
@ -425,15 +426,16 @@ private:
PresetRecord _last_preset; PresetRecord _last_preset;
bool _parameter_changed_since_last_preset; bool _parameter_changed_since_last_preset;
PBD::ScopedConnection _preset_connection;
MidiRingBuffer<samplepos_t> _immediate_events; MidiRingBuffer<samplepos_t> _immediate_events;
std::atomic<bool> _resolve_midi;
void invalidate_preset_cache (std::string const&, Plugin*, bool); void invalidate_preset_cache (std::string const&, Plugin*, bool);
void resolve_midi (); void resolve_midi ();
PluginInsert* _pi; PluginInsert* _pi;
uint32_t _num; uint32_t _num;
PBD::ScopedConnection _preset_connection;
}; };
struct PluginPreset { struct PluginPreset {

View file

@ -95,6 +95,7 @@ Plugin::Plugin (AudioEngine& e, Session& s)
, _have_pending_stop_events (false) , _have_pending_stop_events (false)
, _parameter_changed_since_last_preset (false) , _parameter_changed_since_last_preset (false)
, _immediate_events(6096) // FIXME: size? , _immediate_events(6096) // FIXME: size?
, _resolve_midi (false)
, _pi (0) , _pi (0)
, _num (0) , _num (0)
{ {
@ -116,6 +117,7 @@ Plugin::Plugin (const Plugin& other)
, _last_preset (other._last_preset) , _last_preset (other._last_preset)
, _parameter_changed_since_last_preset (false) , _parameter_changed_since_last_preset (false)
, _immediate_events(6096) // FIXME: size? , _immediate_events(6096) // FIXME: size?
, _resolve_midi (false)
, _pi (other._pi) , _pi (other._pi)
, _num (other._num) , _num (other._num)
{ {
@ -427,6 +429,11 @@ Plugin::connect_and_run (BufferSet& bufs,
} }
} }
bool canderef (true);
if (_resolve_midi.compare_exchange_strong (canderef, false)) {
resolve_midi ();
}
if (_have_pending_stop_events) { if (_have_pending_stop_events) {
/* Transmit note-offs that are pending from the last transport stop */ /* Transmit note-offs that are pending from the last transport stop */
bufs.merge_from (_pending_stop_events, 0); bufs.merge_from (_pending_stop_events, 0);
@ -440,21 +447,21 @@ Plugin::connect_and_run (BufferSet& bufs,
void void
Plugin::realtime_handle_transport_stopped () Plugin::realtime_handle_transport_stopped ()
{ {
resolve_midi (); _resolve_midi = true;
} }
void void
Plugin::realtime_locate (bool for_loop_end) Plugin::realtime_locate (bool for_loop_end)
{ {
if (!for_loop_end) { if (!for_loop_end) {
resolve_midi (); _resolve_midi = true;
} }
} }
void void
Plugin::monitoring_changed () Plugin::monitoring_changed ()
{ {
resolve_midi (); _resolve_midi = true;
} }
void void