summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPaul Davis <paul@linuxaudiosystems.com>2010-05-10 16:05:24 +0000
committerPaul Davis <paul@linuxaudiosystems.com>2010-05-10 16:05:24 +0000
commit37a34bb8b0568ad28fa6c3697a2eab296b0af7ae (patch)
tree058b31ed4887c00f97e34a75645c737542f8b082
parent05b99bf8da5f5b2103bdd27049f691f1638e9dc9 (diff)
use a static per-class signal to notify the selection object in each MidiRegionView when note items are deleted. fixes crash on cut/undo/reselect and related operations
git-svn-id: svn://localhost/ardour2/branches/3.0@7092 d708f5d6-7413-0410-9779-e7cbd77b26cf
-rw-r--r--gtk2_ardour/canvas-note-event.cc4
-rw-r--r--gtk2_ardour/canvas-note-event.h2
-rw-r--r--gtk2_ardour/midi_region_view.cc55
-rw-r--r--gtk2_ardour/midi_region_view.h3
4 files changed, 45 insertions, 19 deletions
diff --git a/gtk2_ardour/canvas-note-event.cc b/gtk2_ardour/canvas-note-event.cc
index 7fdb931ba9..0ad6cd2be9 100644
--- a/gtk2_ardour/canvas-note-event.cc
+++ b/gtk2_ardour/canvas-note-event.cc
@@ -30,6 +30,8 @@ using ARDOUR::MidiModel;
namespace Gnome {
namespace Canvas {
+PBD::Signal1<void,CanvasNoteEvent*> CanvasNoteEvent::CanvasNoteEventDeleted;
+
/// dividing the hue circle in 16 parts, hand adjusted for equal look, courtesy Thorsten Wilms
const uint32_t CanvasNoteEvent::midi_channel_colors[16] = {
0xd32d2dff, 0xd36b2dff, 0xd3972dff, 0xd3d12dff,
@@ -53,7 +55,7 @@ CanvasNoteEvent::CanvasNoteEvent(MidiRegionView& region, Item* item,
CanvasNoteEvent::~CanvasNoteEvent()
{
- cerr << "Destroying CNE @ " << this << endl;
+ CanvasNoteEventDeleted (this);
if (_text) {
_text->hide();
diff --git a/gtk2_ardour/canvas-note-event.h b/gtk2_ardour/canvas-note-event.h
index 9546141d8b..af5dd24102 100644
--- a/gtk2_ardour/canvas-note-event.h
+++ b/gtk2_ardour/canvas-note-event.h
@@ -62,6 +62,8 @@ public:
virtual ~CanvasNoteEvent();
+ static PBD::Signal1<void,CanvasNoteEvent*> CanvasNoteEventDeleted;
+
virtual void show() = 0;
virtual void hide() = 0;
virtual bool on_event(GdkEvent* ev);
diff --git a/gtk2_ardour/midi_region_view.cc b/gtk2_ardour/midi_region_view.cc
index 26490f76e7..f33c15079d 100644
--- a/gtk2_ardour/midi_region_view.cc
+++ b/gtk2_ardour/midi_region_view.cc
@@ -178,6 +178,10 @@ MidiRegionView::MidiRegionView (const MidiRegionView& other, boost::shared_ptr<M
void
MidiRegionView::init (Gdk::Color const & basic_color, bool wfd)
{
+ CanvasNoteEvent::CanvasNoteEventDeleted.connect (note_delete_connection, MISSING_INVALIDATOR,
+ ui_bind (&MidiRegionView::maybe_remove_deleted_note_from_selection, this, _1),
+ gui_context());
+
if (wfd) {
midi_region()->midi_source(0)->load_model();
}
@@ -789,6 +793,8 @@ MidiRegionView::redisplay_model()
MidiModel::Notes& notes (_model->notes());
_optimization_iterator = _events.begin();
+ cerr << "++++++++++ MIDI REdisplay\n";
+
for (MidiModel::Notes::iterator n = notes.begin(); n != notes.end(); ++n) {
boost::shared_ptr<NoteType> note (*n);
@@ -830,6 +836,7 @@ MidiRegionView::redisplay_model()
}
}
+
/* remove note items that are no longer valid */
for (Events::iterator i = _events.begin(); i != _events.end(); ) {
@@ -948,6 +955,8 @@ MidiRegionView::~MidiRegionView ()
{
in_destructor = true;
+ note_delete_connection.disconnect ();
+
delete _list_editor;
RegionViewGoingAway (this); /* EMIT_SIGNAL */
@@ -1473,6 +1482,18 @@ MidiRegionView::next_program(CanvasProgramChange& program)
}
void
+MidiRegionView::maybe_remove_deleted_note_from_selection (CanvasNoteEvent* cne)
+{
+ if (_selection.empty()) {
+ return;
+ }
+
+ if (_selection.erase (cne) > 0) {
+ cerr << "Erased a CNE from selection\n";
+ }
+}
+
+void
MidiRegionView::delete_selection()
{
if (_selection.empty()) {
@@ -1756,7 +1777,6 @@ MidiRegionView::add_to_selection (CanvasNoteEvent* ev)
}
if (_selection.insert (ev).second) {
- cerr << "Added CNE to selection, size now " << _selection.size() << endl;
ev->selected (true);
play_midi_note ((ev)->note());
}
@@ -2453,21 +2473,23 @@ MidiRegionView::cut_copy_clear (Editing::CutCopyOp op)
break;
}
- start_delta_command();
+ if (op != Copy) {
- for (Selection::iterator i = _selection.begin(); i != _selection.end(); ++i) {
- switch (op) {
- case Copy:
- break;
- case Cut:
- delta_remove_note (*i);
- break;
- case Clear:
- break;
- }
- }
-
- apply_delta();
+ start_delta_command();
+
+ for (Selection::iterator i = _selection.begin(); i != _selection.end(); ++i) {
+ switch (op) {
+ case Copy:
+ break;
+ case Cut:
+ case Clear:
+ delta_remove_note (*i);
+ break;
+ }
+ }
+
+ apply_delta();
+ }
}
MidiCutBuffer*
@@ -2475,11 +2497,8 @@ MidiRegionView::selection_as_cut_buffer () const
{
Notes notes;
- cerr << "Convert selection of " << _selection.size() << " into a cut buffer\n";
-
for (Selection::iterator i = _selection.begin(); i != _selection.end(); ++i) {
NoteType* n = (*i)->note().get();
- cerr << "CNE's note is " << n << endl;
notes.insert (boost::shared_ptr<NoteType> (new NoteType (*n)));
}
diff --git a/gtk2_ardour/midi_region_view.h b/gtk2_ardour/midi_region_view.h
index d6dd213e72..ea05953080 100644
--- a/gtk2_ardour/midi_region_view.h
+++ b/gtk2_ardour/midi_region_view.h
@@ -403,6 +403,9 @@ class MidiRegionView : public RegionView
MidiListEditor* _list_editor;
bool no_sound_notes;
+
+ PBD::ScopedConnection note_delete_connection;
+ void maybe_remove_deleted_note_from_selection (ArdourCanvas::CanvasNoteEvent*);
};