diff options
author | Paul Davis <paul@linuxaudiosystems.com> | 2010-05-10 16:05:24 +0000 |
---|---|---|
committer | Paul Davis <paul@linuxaudiosystems.com> | 2010-05-10 16:05:24 +0000 |
commit | 37a34bb8b0568ad28fa6c3697a2eab296b0af7ae (patch) | |
tree | 058b31ed4887c00f97e34a75645c737542f8b082 | |
parent | 05b99bf8da5f5b2103bdd27049f691f1638e9dc9 (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.cc | 4 | ||||
-rw-r--r-- | gtk2_ardour/canvas-note-event.h | 2 | ||||
-rw-r--r-- | gtk2_ardour/midi_region_view.cc | 55 | ||||
-rw-r--r-- | gtk2_ardour/midi_region_view.h | 3 |
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*); }; |