95
100
Segment &segment(getSegment());
96
101
SegmentNotationHelper helper(segment);
98
// If we're attempting to insert at the same time and pitch as an
99
// existing note, then we remove the existing note first (so as to
100
// change its duration, if the durations differ)
101
102
Segment::iterator i, j;
102
segment.getTimeSlice(m_insertionTime, i, j);
104
if ((*i)->isa(Note::EventType)) {
107
<Int>(PITCH, pitch) && pitch == m_pitch) {
108
helper.deleteNote(*i);
115
104
// insert via a model event, so as to apply the note style
118
(Note::EventType, m_insertionTime, m_note.getDuration());
121
<Int>(PITCH, m_pitch);
123
<Int>(VELOCITY, 100);
106
// subordering is always negative for these insertions; round it down
107
int actualSubordering = lrintf(floorf(m_targetSubordering + 0.01));
108
if ((m_grace != GraceModeOff) && actualSubordering >= 0) {
109
actualSubordering = -1;
112
// this is true if the subordering is "more or less" an integer,
113
// as opposed to something like -0.5
114
bool suborderingExact = (actualSubordering !=
115
(lrintf(floorf(m_targetSubordering - 0.01))));
117
std::cerr << "actualSubordering = " << actualSubordering
118
<< " suborderingExact = " << suborderingExact << std::endl;
122
if (m_grace == GraceModeOff) {
127
m_note.getDuration(),
130
m_note.getDuration());
138
actualSubordering == 0 ? -1 : actualSubordering,
140
m_note.getDuration());
143
e->set<Int>(PITCH, m_pitch);
144
e->set<Int>(VELOCITY, 100);
125
146
if (m_accidental != Accidentals::NoAccidental) {
127
<String>(ACCIDENTAL, m_accidental);
147
e->set<String>(ACCIDENTAL, m_accidental);
130
150
if (m_noteStyle != NoteStyleFactory::DefaultStyle) {
132
<String>(NotationProperties::NOTE_STYLE, m_noteStyle);
151
e->set<String>(NotationProperties::NOTE_STYLE, m_noteStyle);
136
i = SegmentMatrixHelper(segment).insertNote(e);
154
if (m_grace != GraceModeOff) {
156
if (!suborderingExact) {
158
// Adjust suborderings of any existing grace notes, if there
159
// is at least one with the same subordering and
160
// suborderingExact is not set
162
segment.getTimeSlice(m_insertionTime, i, j);
163
bool collision = false;
164
for (Segment::iterator k = i; k != j; ++k) {
165
if ((*k)->getSubOrdering() == actualSubordering) {
172
std::vector<Event *> toInsert, toErase;
173
for (Segment::iterator k = i; k != j; ++k) {
174
if ((*k)->isa(Note::EventType) &&
175
(*k)->getSubOrdering() <= actualSubordering) {
176
toErase.push_back(*k);
179
(*k)->getAbsoluteTime(),
181
(*k)->getSubOrdering() - 1,
182
(*k)->getNotationAbsoluteTime(),
183
(*k)->getNotationDuration()));
186
for (std::vector<Event *>::iterator k = toErase.begin();
187
k != toErase.end(); ++k) segment.eraseSingle(*k);
188
for (std::vector<Event *>::iterator k = toInsert.begin();
189
k != toInsert.end(); ++k) segment.insert(*k);
193
e->set<Bool>(IS_GRACE_NOTE, true);
194
i = segment.insert(e);
197
segment.getTimeSlice(m_insertionTime, j, k);
198
Segment::iterator bg0 = segment.end(), bg1 = segment.end();
200
std::cerr << "testing for truthiness: time " << (*j)->getAbsoluteTime() << ", subordering " << (*j)->getSubOrdering() << std::endl;
201
if ((*j)->isa(Note::EventType) &&
202
(*j)->getSubOrdering() < 0 &&
203
(*j)->has(IS_GRACE_NOTE) &&
204
(*j)->get<Bool>(IS_GRACE_NOTE)) {
205
std::cerr << "truthiful" << std::endl;
206
if (bg0 == segment.end()) bg0 = j;
212
if (bg0 != segment.end() && bg1 != bg0) {
213
if (bg1 != segment.end()) ++bg1;
216
for (Segment::iterator i = bg0; i != bg1; ++i) {
217
(*i)->unset(BEAMED_GROUP_ID);
218
(*i)->unset(BEAMED_GROUP_TYPE);
219
(*i)->unset(BEAMED_GROUP_TUPLED_COUNT);
220
(*i)->unset(BEAMED_GROUP_UNTUPLED_COUNT);
221
if ((*i)->getSubOrdering() != pso) {
223
pso = (*i)->getSubOrdering();
226
if (m_grace == GraceAndTripletModesOn) {
227
helper.makeBeamedGroupExact(bg0, bg1, GROUP_TYPE_TUPLED);
229
for (Segment::iterator i = bg0; i != bg1; ++i) {
230
(*i)->set<Int>(BEAMED_GROUP_TUPLED_COUNT, count-1);
231
(*i)->set<Int>(BEAMED_GROUP_UNTUPLED_COUNT, count);
235
helper.makeBeamedGroupExact(bg0, bg1, GROUP_TYPE_BEAMED);
138
i = helper.insertNote(e);
139
// e is just a model for SegmentNotationHelper::insertNote
241
// If we're attempting to insert at the same time and pitch as
242
// an existing note, then we remove the existing note first
243
// (so as to change its duration, if the durations differ)
244
segment.getTimeSlice(m_insertionTime, i, j);
246
if ((*i)->isa(Note::EventType)) {
248
if ((*i)->get<Int>(PITCH, pitch) && pitch == m_pitch) {
249
helper.deleteNote(*i);
257
i = SegmentMatrixHelper(segment).insertNote(e);
259
i = helper.insertNote(e);
260
// e is just a model for SegmentNotationHelper::insertNote
143
if (i != segment.end())
144
m_lastInsertedEvent = *i;
265
if (i != segment.end()) m_lastInsertedEvent = *i;
146
267
if (m_autoBeam) {