Piano renders as percussion on SMF import with Yamaha XG SysEx block
If an SMF contains a Yamaha SysEx block, then the routine which recognises PartMode as Percussion kicks in on all channels and erroneously sets the Part to Drumkit in the mixer.
Details here.....
https://musescore.org/en/node/82241
The routine is applying Percussion PartMode to channels not set to Percussion in the SysEx block.
If you need to know more about Yamaha XG SysEx then ask me - I am very knowledgable on the subject.
Comments
certainly not critical, is it?
Critical - it's a corruption of data.
On reflection major is better - forgot we'd added that.
I've just been taking a look at the code which can be found at line 785 of midifile.cpp
It checks through the SysEx block to see if PartMode is set to anything other than 0 and if that is the case sets the track to be a drum track.
The flaw in this logic, however, is that if the MIDI file format is 0 there is only 1 track or - if the format is 1 but there is only one instrument. Consequently, as the routine is not taking channel into account it is setting the track as a drum track even though the channel for the data is other than that specified in the SysEx block.
The code needs modifying to check that the Channel for the PartMode set <> 0 is the same as the channel for the rest of the track.
You mean this line ?
No that's where the XG stuff starts
The actual checkfor PartMode comes 5 lines later...
Here
The specific lines which set the track as a Drum track start here.....
Line 798
It needs to be altered to something like
if (buffer[6] != 0 && buffer[4] == Channel )
{
_drumTrack = true;
}
But I have no idea where the MIDI Channel is stored or how to pass it to the sub routine
PR: https://github.com/musescore/MuseScore/pull/2395
@ChurchOrganist: You practically had it. Here's how to get the channel at this point in the code.
This fully fixes this issue as it is currently worded, but a related issue remains: if the SysEx event is not referring to the current track and channel, how can we set _drumTrack = true on the track and channel it is referring to? This requires the current track to be "aware of" and have access to all of the other tracks, and this is not currently possible without major restructuring of the code. Additionally, the way MuseScore handles MIDI tracks vs MIDI channels is not helpful for this. Fortunately, this issue is largely theoretical because if the drum track is the 10th channel (channel=9), which it will be for all standards-compliant MIDI files, then it will be rendered as a drum track anyway. It's also possible that the SysEx event will be repeated on the relevant track in which case it will be set as a drum track then.
Fixed in branch master, commit b8a79f4fb6
Fix #85856: MIDI import - better handling of Yamaha SG SysEx block
Fixed in branch master, commit 5c16d56159
Merge pull request #2395 from shoogle/85856-midi-import-yamaha-sysex-drumkit
Fix #85856: MIDI import - better handling of Yamaha SG SysEx block
Fixed in branch 2.0.3, commit b797f81bea
Fix #85856: MIDI import - better handling of Yamaha SG SysEx block
Automatically closed -- issue fixed for 2 weeks with no activity.