From f27dc9ee8f7501d86b1b3d7aecf447692cddd636 Mon Sep 17 00:00:00 2001 From: Matthias Neeracher Date: Sun, 28 Aug 2011 21:54:20 +0200 Subject: [PATCH] Successfully round trip accidentals in chords --- Filters/VLMusicXMLType.reader | 11 ++++++++++- Filters/VLMusicXMLType.writer | 19 +++++++++++-------- Sources/VLPListDocument.mm | 9 ++++++++- 3 files changed, 29 insertions(+), 10 deletions(-) diff --git a/Filters/VLMusicXMLType.reader b/Filters/VLMusicXMLType.reader index 33f22d9..410b1f4 100755 --- a/Filters/VLMusicXMLType.reader +++ b/Filters/VLMusicXMLType.reader @@ -305,6 +305,7 @@ class MusicXMLListener end end + ACC = [VL::Want2Flat, VL::WantFlat, 0, VL::WantSharp, VL::Want2Sharp] def tag_end(tag) # # Interesting text nodes have @kind set @@ -331,8 +332,13 @@ class MusicXMLListener @prop['mode'] = @text == 'minor' ? -1 : 1 when 'step' @note['pitch'] += PITCH[@text] - when 'alter', 'root-alter' + when 'alter' + @note['pitch'] += @text.to_i + when 'root-alter' @note['pitch'] += @text.to_i + if @text.to_i != 0 + @note['visual'] = ACC[@text.to_i+2] + end when 'octave' @note['pitch'] += (@text.to_i+1)*12 when 'duration' @@ -359,6 +365,9 @@ class MusicXMLListener @note['root'] = PITCH[@text] when 'bass-alter' @note['root'] += @text.to_i + if @text.to_i != 0 + @note['rootvisual'] = ACC[@text.to_i+2] + end when 'kind' @note['steps'] = CHORD[@text] when 'degree-value' diff --git a/Filters/VLMusicXMLType.writer b/Filters/VLMusicXMLType.writer index 0d8db4a..03c1011 100755 --- a/Filters/VLMusicXMLType.writer +++ b/Filters/VLMusicXMLType.writer @@ -101,7 +101,7 @@ end STEPS = ' BC D EF G A B C ' def _pitch(name, pitch, accidental, prefix="") - pitch-= accidental + pitch-= accidental ? accidental : 0 oct = pitch/12 - 1 stp = (pitch%12)+2 step = STEPS[stp] @@ -126,7 +126,7 @@ end TYPE = %w[whole half quarter eighth 16th 32nd] ACC = %w[flat-flat flat natural sharp double-sharp] -def _note(pitch, dur, visual, tied) +def _accidental(visual) accidental = nil case visual & VL::Accidentals when VL::Want2Flat @@ -140,6 +140,11 @@ def _note(pitch, dur, visual, tied) when VL::Want2Sharp accidental = 2 end + accidental +end + +def _note(pitch, dur, visual, tied) + accidental = _accidental(visual) note = REXML::Element.new('note') if pitch == VL::NoPitch note.add_element(REXML::Element.new('rest')) @@ -235,9 +240,7 @@ DEGREE = [ [VL::Dim13th+VL::Min13th+VL::Maj13th, VL::Maj13th] ]; -def _chord(pitch, visual, steps, root) - preferFlats = (visual & VL::WantSharp) == 0 && - ((visual & VL::WantFlat) != 0 || $USE_FLATS) +def _chord(pitch, visual, steps, root, rootVisual) # # Pick kind. sus takes precedence # @@ -272,10 +275,10 @@ def _chord(pitch, visual, steps, root) end end harm = REXML::Element.new('harmony') - harm.add_element(_pitch('root', pitch, visual, 'root')) + harm.add_element(_pitch('root', pitch, _accidental(visual), 'root')) harm.add_element newTextElement('kind', kind) if root != VL::NoPitch - harm.add_element(_pitch('bass', root, visual, 'bass')) + harm.add_element(_pitch('bass', root, _accidental(rootVisual), 'bass')) end needSteps = steps & ~CHORD[kind] extraSteps= CHORD[kind] & ~steps @@ -398,7 +401,7 @@ def _melody m.add_element(fw) tempAt = chordAt end - m.add_element(_chord(chord['pitch'], chord['visual'], chord['steps'], chord['root'])) + m.add_element(_chord(chord['pitch'], chord['visual'], chord['steps'], chord['root'], chord['rootvisual'])) end chordAt += (chord['durNum'] * $DIVISIONS * 4) / chord['durDenom'] chordIx += 1 diff --git a/Sources/VLPListDocument.mm b/Sources/VLPListDocument.mm index 638f7cf..3a20f6d 100644 --- a/Sources/VLPListDocument.mm +++ b/Sources/VLPListDocument.mm @@ -156,14 +156,19 @@ void VLPlistVisitor::VisitNote(VLLyricsNote & n) void VLPlistVisitor::VisitChord(VLChord & c) { + int pitchGrid = VLPitchToGrid(c.fPitch, c.fVisual, 0); + VLVisualFilter pitchFilter(0); + int rootGrid = VLPitchToGrid(c.fRootPitch, c.fRootAccidental, 0); + VLVisualFilter rootFilter(0); NSDictionary * cd = [NSDictionary dictionaryWithObjectsAndKeys: [NSNumber numberWithInt:c.fDuration.fNum], @"durNum", [NSNumber numberWithInt:c.fDuration.fDenom], @"durDenom", [NSNumber numberWithInt:c.fPitch], @"pitch", - [NSNumber numberWithInt:c.fVisual], @"visual", + [NSNumber numberWithInt:pitchFilter(pitchGrid, c.fVisual)], @"visual", [NSNumber numberWithInt:c.fSteps], @"steps", [NSNumber numberWithInt:c.fRootPitch], @"root", + [NSNumber numberWithInt:rootFilter(rootGrid, c.fRootAccidental)], @"rootvisual", nil]; [fChords addObject: cd]; } @@ -336,7 +341,9 @@ advanceAt: [[cdict objectForKey:@"durDenom"] intValue], true); chord.fPitch = [[cdict objectForKey:@"pitch"] intValue]; + chord.fVisual = [[cdict objectForKey:@"visual"] intValue]; chord.fRootPitch = [[cdict objectForKey:@"root"] intValue]; + chord.fRootAccidental = [[cdict objectForKey:@"rootvisual"] intValue]; chord.fSteps = [[cdict objectForKey:@"steps"] intValue]; song->AddChord(chord, measNo, at);