X-Git-Url: https://main.carlh.net/gitweb/?a=blobdiff_plain;f=gtk2_ardour%2Fghostregion.cc;h=06946ec7ec8f45bc6333697384bea3f13ce19453;hb=61d26e5678de2738120c5be9832d4e9c480d3c47;hp=959f5ae82cb0dfba132667868683e5044a5c710a;hpb=cee7e0cb53d0bf271548bc4c6cc9ea27906f44ef;p=ardour.git diff --git a/gtk2_ardour/ghostregion.cc b/gtk2_ardour/ghostregion.cc index 959f5ae82c..06946ec7ec 100644 --- a/gtk2_ardour/ghostregion.cc +++ b/gtk2_ardour/ghostregion.cc @@ -17,20 +17,23 @@ */ +#include "evoral/Note.hpp" + #include "ardour/parameter_descriptor.h" -#include "evoral/Note.hpp" #include "canvas/container.h" #include "canvas/polygon.h" #include "canvas/rectangle.h" -#include "canvas/wave_view.h" #include "canvas/debug.h" +#include "waveview/wave_view.h" + #include "automation_time_axis.h" #include "ghostregion.h" #include "midi_streamview.h" #include "midi_time_axis.h" #include "region_view.h" +#include "midi_region_view.h" #include "rgb_macros.h" #include "note.h" #include "hit.h" @@ -38,8 +41,8 @@ using namespace std; using namespace Editing; -using namespace ArdourCanvas; using namespace ARDOUR; +using ArdourCanvas::Duple; GhostRegion::GhostRegion(RegionView& rv, ArdourCanvas::Container* parent, @@ -125,7 +128,7 @@ AudioGhostRegion::AudioGhostRegion(RegionView& rv, void AudioGhostRegion::set_samples_per_pixel (double fpp) { - for (vector::iterator i = waves.begin(); i != waves.end(); ++i) { + for (vector::iterator i = waves.begin(); i != waves.end(); ++i) { (*i)->set_samples_per_pixel (fpp); } } @@ -133,7 +136,7 @@ AudioGhostRegion::set_samples_per_pixel (double fpp) void AudioGhostRegion::set_height () { - vector::iterator i; + vector::iterator i; uint32_t n; GhostRegion::set_height(); @@ -174,12 +177,13 @@ AudioGhostRegion::set_colors () * @param tv TimeAxisView that this ghost region is on. * @param source_tv TimeAxisView that we are the ghost for. */ -MidiGhostRegion::MidiGhostRegion(RegionView& rv, +MidiGhostRegion::MidiGhostRegion(MidiRegionView& rv, TimeAxisView& tv, TimeAxisView& source_tv, double initial_unit_pos) : GhostRegion(rv, tv.ghost_group(), tv, source_tv, initial_unit_pos) , _note_group (new ArdourCanvas::Container (group)) + , parent_mrv (rv) , _optimization_iterator(events.end()) { _outline = UIConfiguration::instance().color ("ghost track midi outline"); @@ -192,7 +196,7 @@ MidiGhostRegion::MidiGhostRegion(RegionView& rv, * @param msv MidiStreamView that this ghost region is on. * @param source_tv TimeAxisView that we are the ghost for. */ -MidiGhostRegion::MidiGhostRegion(RegionView& rv, +MidiGhostRegion::MidiGhostRegion(MidiRegionView& rv, MidiStreamView& msv, TimeAxisView& source_tv, double initial_unit_pos) @@ -202,6 +206,7 @@ MidiGhostRegion::MidiGhostRegion(RegionView& rv, source_tv, initial_unit_pos) , _note_group (new ArdourCanvas::Container (group)) + , parent_mrv (rv) , _optimization_iterator(events.end()) { _outline = UIConfiguration::instance().color ("ghost track midi outline"); @@ -222,6 +227,7 @@ MidiGhostRegion::GhostEvent::GhostEvent (NoteBase* e, ArdourCanvas::Container* g if (dynamic_cast(e)) { item = new ArdourCanvas::Rectangle( g, ArdourCanvas::Rect(e->x0(), e->y0(), e->x1(), e->y1())); + is_hit = false; } else { Hit* hit = dynamic_cast(e); if (!hit) { @@ -231,6 +237,7 @@ MidiGhostRegion::GhostEvent::GhostEvent (NoteBase* e, ArdourCanvas::Container* g poly->set(Hit::points(e->y1() - e->y0())); poly->set_position(hit->position()); item = poly; + is_hit = true; } CANVAS_DEBUG_NAME (item, "ghost note item"); @@ -273,8 +280,8 @@ MidiGhostRegion::set_colors() _outline = UIConfiguration::instance().color ("ghost track midi outline"); for (EventList::iterator it = events.begin(); it != events.end(); ++it) { - (*it).second->item->set_fill_color (UIConfiguration::instance().color_mod((*it).second->event->base_color(), "ghost track midi fill")); - (*it).second->item->set_outline_color (_outline); + it->second->item->set_fill_color (UIConfiguration::instance().color_mod((*it).second->event->base_color(), "ghost track midi fill")); + it->second->item->set_outline_color (_outline); } } @@ -309,14 +316,16 @@ MidiGhostRegion::update_contents_height () double const h = note_height(trackview, mv); for (EventList::iterator it = events.begin(); it != events.end(); ++it) { - uint8_t const note_num = (*it).second->event->note()->note(); + uint8_t const note_num = it->second->event->note()->note(); double const y = note_y(trackview, mv, note_num); - if ((_tmp_rect = dynamic_cast((*it).second->item))) { + if (!it->second->is_hit) { + _tmp_rect = static_cast(it->second->item); _tmp_rect->set (ArdourCanvas::Rect (_tmp_rect->x0(), y, _tmp_rect->x1(), y + h)); - } else if ((_tmp_poly = dynamic_cast((*it).second->item))) { - Duple position = _tmp_poly->position(); + } else { + _tmp_poly = static_cast(it->second->item); + ArdourCanvas::Duple position = _tmp_poly->position(); position.y = y; _tmp_poly->set_position(position); _tmp_poly->set(Hit::points(h)); @@ -336,17 +345,18 @@ MidiGhostRegion::add_note (NoteBase* n) MidiStreamView* mv = midi_view(); if (mv) { - uint8_t const note_num = n->note()->note(); - double const h = note_height(trackview, mv); - double const y = note_y(trackview, mv, note_num); - if (n->x0() < base_rect->x0() || n->x1() > base_rect->x1()) { - event->item->hide(); - } else if (note_num < mv->lowest_note() || note_num > mv->highest_note()) { + + if (!n->item()->visible()) { event->item->hide(); } else { - if ((_tmp_rect = dynamic_cast(event->item))) { + uint8_t const note_num = n->note()->note(); + double const h = note_height(trackview, mv); + double const y = note_y(trackview, mv, note_num); + if (!event->is_hit) { + _tmp_rect = static_cast(event->item); _tmp_rect->set (ArdourCanvas::Rect (_tmp_rect->x0(), y, _tmp_rect->x1(), y + h)); - } else if ((_tmp_poly = dynamic_cast(event->item))) { + } else { + _tmp_poly = static_cast(event->item); Duple position = _tmp_poly->position(); position.y = y; _tmp_poly->set_position(position); @@ -364,11 +374,11 @@ MidiGhostRegion::clear_events() _optimization_iterator = events.end(); } -/** Update the x positions of our representation of a parent's note. - * @param parent The CanvasNote from the parent MidiRegionView. +/** Update the positions of our representation of a note. + * @param ev The GhostEvent from the parent MidiRegionView. */ void -MidiGhostRegion::update_note (Note* note, bool hide) +MidiGhostRegion::update_note (GhostEvent* ev) { MidiStreamView* mv = midi_view(); @@ -376,32 +386,20 @@ MidiGhostRegion::update_note (Note* note, bool hide) return; } - GhostEvent* ev = find_event (note); - - if (!ev) { - return; - } - - uint8_t const note_num = note->note()->note(); + _tmp_rect = static_cast(ev->item); + uint8_t const note_num = ev->event->note()->note(); double const y = note_y(trackview, mv, note_num); double const h = note_height(trackview, mv); - if (hide) { - ev->item->hide(); - } else { - if ((_tmp_rect = dynamic_cast(ev->item))) { - _tmp_rect->set (ArdourCanvas::Rect (note->x0(), y, note->x1(), y + h)); - } - ev->item->show(); - } + _tmp_rect->set (ArdourCanvas::Rect (ev->event->x0(), y, ev->event->x1(), y + h)); } -/** Update the x positions of our representation of a parent's hit. - * @param hit The CanvasHit from the parent MidiRegionView. +/** Update the positions of our representation of a parent's hit. + * @param ev The GhostEvent from the parent MidiRegionView. */ void -MidiGhostRegion::update_hit (Hit* hit, bool hide) +MidiGhostRegion::update_hit (GhostEvent* ev) { MidiStreamView* mv = midi_view(); @@ -409,29 +407,19 @@ MidiGhostRegion::update_hit (Hit* hit, bool hide) return; } - GhostEvent* ev = find_event (hit); - - if (!ev) { - return; - } + _tmp_poly = static_cast(ev->item); uint8_t const note_num = ev->event->note()->note(); - double const h = note_height(trackview, mv); double const y = note_y(trackview, mv, note_num); - if (hide) { - ev->item->hide(); - } else { - if ((_tmp_poly = dynamic_cast(ev->item))) { - ArdourCanvas::Duple ppos = hit->position(); - ArdourCanvas::Duple gpos = _tmp_poly->position(); - gpos.x = ppos.x; - gpos.y = y; - _tmp_poly->set_position(gpos); - _tmp_poly->set(Hit::points(h)); - } - ev->item->show(); - } + + ArdourCanvas::Duple ppos = ev->item->position(); + ArdourCanvas::Duple gpos = _tmp_poly->position(); + gpos.x = ppos.x; + gpos.y = y; + + _tmp_poly->set_position(gpos); + _tmp_poly->set(Hit::points(h)); } void @@ -442,11 +430,36 @@ MidiGhostRegion::remove_note (NoteBase* note) return; } - delete (*f).second; + delete f->second; events.erase (f); _optimization_iterator = events.end (); } +void +MidiGhostRegion::redisplay_model () +{ + /* we rely on the parent MRV having removed notes not in the model */ + for (EventList::iterator i = events.begin(); i != events.end(); ) { + + boost::shared_ptr note = i->first; + GhostEvent* cne = i->second; + const bool visible = (note->note() >= parent_mrv._current_range_min) && + (note->note() <= parent_mrv._current_range_max); + + if (visible) { + if (cne->is_hit) { + update_hit (cne); + } else { + update_note (cne); + } + cne->item->show (); + } else { + cne->item->hide (); + } + + ++i; + } +} /** Given a note in our parent region (ie the actual MidiRegionView), find our * representation of it. @@ -454,7 +467,7 @@ MidiGhostRegion::remove_note (NoteBase* note) */ MidiGhostRegion::GhostEvent * -MidiGhostRegion::find_event (NoteBase* parent) +MidiGhostRegion::find_event (boost::shared_ptr parent) { /* we are using _optimization_iterator to speed up the common case where a caller is going through our notes in order. @@ -462,14 +475,14 @@ MidiGhostRegion::find_event (NoteBase* parent) if (_optimization_iterator != events.end()) { ++_optimization_iterator; - if (_optimization_iterator != events.end() && (*_optimization_iterator).second->event == parent) { - return (*_optimization_iterator).second; + if (_optimization_iterator != events.end() && _optimization_iterator->first == parent) { + return _optimization_iterator->second; } } - _optimization_iterator = events.find (parent->note()); + _optimization_iterator = events.find (parent); if (_optimization_iterator != events.end()) { - return (*_optimization_iterator).second; + return _optimization_iterator->second; } return 0;