+ _note_iter = model.notes().end();
+
+ for (MidiModel::Notes::const_iterator i = model.notes().begin(); i != model.notes().end(); ++i) {
+ if ((*i).time() >= t) {
+ _note_iter = i;
+ break;
+ }
+ }
+
+ MidiControlIterator earliest_control = make_pair(boost::shared_ptr<AutomationList>(),
+ make_pair(DBL_MAX, 0.0));
+
+ _control_iters.reserve(model.controls().size());
+ for (Automatable::Controls::const_iterator i = model.controls().begin();
+ i != model.controls().end(); ++i) {
+
+ assert(i->first.type() == MidiCCAutomation);
+
+ double x, y;
+ bool ret = i->second->list()->rt_safe_earliest_event_unlocked(t, DBL_MAX, x, y);
+ if (!ret) {
+ cerr << "MIDI Iterator: CC " << i->first.id() << " (size " << i->second->list()->size()
+ << ") has no events past " << t << endl;
+ continue;
+ }
+
+ assert(x >= 0);
+ assert(y >= 0);
+ assert(y <= UINT8_MAX);
+
+ const MidiControlIterator new_iter = make_pair(i->second->list(), make_pair(x, y));
+
+ //cerr << "MIDI Iterator: CC " << i->first.id() << " added (" << x << ", " << y << ")" << endl;
+ _control_iters.push_back(new_iter);
+
+ if (x < earliest_control.second.first) {
+ earliest_control = new_iter;
+ _control_iter = _control_iters.end();
+ --_control_iter;
+ }
+ }
+
+ if (_note_iter != model.notes().end()) {
+ _event = MidiEvent(_note_iter->on_event(), false);
+ ++_note_iter;
+ }
+
+ if (earliest_control.first && earliest_control.second.first < _event.time())
+ model.control_to_midi_event(_event, earliest_control);
+ else
+ _control_iter = _control_iters.end();
+
+ if (_event.size() == 0) {
+ //cerr << "Created MIDI iterator @ " << t << " is at end." << endl;
+ _is_end = true;
+ _model->read_unlock();
+ _locked = false;
+ //} else {
+ // printf("MIDI Iterator = %X @ %lf\n", _event.type(), _event.time());
+ }