muse-sequencer / muse

MusE is a digital audio workstation with support for both Audio and MIDI
https://muse-sequencer.github.io/
Other
651 stars 69 forks source link

inaccuracy on events timing when recording midi from muse to external sequencer #920

Closed YievCkim closed 1 year ago

YievCkim commented 3 years ago

Hello,

I have a Korg Kronos2 and muse 3.1.1 which runs on Arch Linux. When I drive my synth from Muse everything works. But If I try to record a midi song from muse to Kronos internal sequencer events are recorded in advance. The Korg sequencer as a resolution of 480ppqn. With a song at 130bpm events are recorded with an advance of roughly 20ppqn.

I don't know If can do something for that. I have tried to adjust Send sync delay in midi sync dialog, but this didn't change anything.

here the output yield by muse when I try from command line:

$ LANG=C muse3
Config File </home/mik/.config/MusE/MusE/MusE-seq.cfg>
LOCALE C
Initializing Native VST support. Using VESTIGE compatibility implementation.
lilv_world_add_plugin(): warning: Duplicate plugin <http://lv2plug.in/plugins/eg-fifths>
lilv_world_add_plugin(): warning: ... found in file:///usr/lib64/lv2/eg-fifths.lv2/
lilv_world_add_plugin(): warning: ... and      file:///usr/lib/lv2/eg-fifths.lv2/ (ignored)
lilv_world_add_plugin(): warning: Duplicate plugin <http://lv2plug.in/plugins/eg-amp>
lilv_world_add_plugin(): warning: ... found in file:///usr/lib64/lv2/eg-amp.lv2/
lilv_world_add_plugin(): warning: ... and      file:///usr/lib/lv2/eg-amp.lv2/ (ignored)
lilv_world_add_plugin(): warning: Duplicate plugin <http://lv2plug.in/plugins/eg-params>
lilv_world_add_plugin(): warning: ... found in file:///usr/lib64/lv2/eg-params.lv2/
lilv_world_add_plugin(): warning: ... and      file:///usr/lib/lv2/eg-params.lv2/ (ignored)
lilv_world_add_plugin(): warning: Duplicate plugin <http://lv2plug.in/plugins/eg-midigate>
lilv_world_add_plugin(): warning: ... found in file:///usr/lib64/lv2/eg-midigate.lv2/
lilv_world_add_plugin(): warning: ... and      file:///usr/lib/lv2/eg-midigate.lv2/ (ignored)
lilv_world_add_plugin(): warning: Duplicate plugin <http://lv2plug.in/plugins/eg-scope#Mono>
lilv_world_add_plugin(): warning: ... found in file:///usr/lib64/lv2/eg-scope.lv2/
lilv_world_add_plugin(): warning: ... and      file:///usr/lib/lv2/eg-scope.lv2/ (ignored)
lilv_world_add_plugin(): warning: Duplicate plugin <http://lv2plug.in/plugins/eg-scope#Stereo>
lilv_world_add_plugin(): warning: ... found in file:///usr/lib64/lv2/eg-scope.lv2/
lilv_world_add_plugin(): warning: ... and      file:///usr/lib/lv2/eg-scope.lv2/ (ignored)
lilv_world_add_plugin(): warning: Duplicate plugin <http://lv2plug.in/plugins/eg-sampler>
lilv_world_add_plugin(): warning: ... found in file:///usr/lib64/lv2/eg-sampler.lv2/
lilv_world_add_plugin(): warning: ... and      file:///usr/lib/lv2/eg-sampler.lv2/ (ignored)
lilv_world_add_plugin(): warning: Duplicate plugin <http://lv2plug.in/plugins/eg-metro>
lilv_world_add_plugin(): warning: ... found in file:///usr/lib64/lv2/eg-metro.lv2/
lilv_world_add_plugin(): warning: ... and      file:///usr/lib/lv2/eg-metro.lv2/ (ignored)
Denormal protection enabled.
Select audio device from configuration : 0
User JackAudio backend - backend selected through configuration
MusE:initJackAudio: jack_get_version() returned zeros. Setting version major to 1.
Using Jack
Trying RTC timer...
got timer = 34
Ignoring DSSI effect label:karplong uri: path:/usr/lib/dssi/karplong.so duplicate of path:/usr/lib64/dssi/karplong.so
Ignoring DSSI effect label:LTS uri: path:/usr/lib/dssi/less_trivial_synth.so duplicate of path:/usr/lib64/dssi/less_trivial_synth.so
Ignoring DSSI effect label:stereo_sampler uri: path:/usr/lib/dssi/trivial_sampler.so duplicate of path:/usr/lib64/dssi/trivial_sampler.so
Ignoring DSSI effect label:mono_sampler uri: path:/usr/lib/dssi/trivial_sampler.so duplicate of path:/usr/lib64/dssi/trivial_sampler.so
Ignoring DSSI effect label:TS uri: path:/usr/lib/dssi/trivial_synth.so duplicate of path:/usr/lib64/dssi/trivial_synth.so
Ignoring LADSPA effect label:amp_mono uri: path:/usr/lib/ladspa/amp.so duplicate of path:/usr/lib64/ladspa/amp.so
Ignoring LADSPA effect label:amp_stereo uri: path:/usr/lib/ladspa/amp.so duplicate of path:/usr/lib64/ladspa/amp.so
Ignoring LADSPA effect label:delay_5s uri: path:/usr/lib/ladspa/delay.so duplicate of path:/usr/lib64/ladspa/delay.so
Ignoring LADSPA effect label:lpf uri: path:/usr/lib/ladspa/filter.so duplicate of path:/usr/lib64/ladspa/filter.so
Ignoring LADSPA effect label:hpf uri: path:/usr/lib/ladspa/filter.so duplicate of path:/usr/lib64/ladspa/filter.so
Ignoring LADSPA effect label:rubberband-pitchshifter-mono uri: path:/usr/lib/ladspa/ladspa-rubberband.so duplicate of path:/usr/lib64/ladspa/ladspa-rubberband.so
Ignoring LADSPA effect label:rubberband-pitchshifter-stereo uri: path:/usr/lib/ladspa/ladspa-rubberband.so duplicate of path:/usr/lib64/ladspa/ladspa-rubberband.so
Ignoring LADSPA effect label:noise_white uri: path:/usr/lib/ladspa/noise.so duplicate of path:/usr/lib64/ladspa/noise.so
Ignoring LADSPA effect label:sine_faaa uri: path:/usr/lib/ladspa/sine.so duplicate of path:/usr/lib64/ladspa/sine.so
Ignoring LADSPA effect label:sine_faac uri: path:/usr/lib/ladspa/sine.so duplicate of path:/usr/lib64/ladspa/sine.so
Ignoring LADSPA effect label:sine_fcaa uri: path:/usr/lib/ladspa/sine.so duplicate of path:/usr/lib64/ladspa/sine.so
Ignoring LADSPA effect label:sine_fcac uri: path:/usr/lib/ladspa/sine.so duplicate of path:/usr/lib64/ladspa/sine.so
Initializing Native VST support. Using VESTIGE compatibility implementation.
Ignoring DSSI synth label:karplong uri: path:/usr/lib/dssi/karplong.so duplicate of path:/usr/lib64/dssi/karplong.so
Ignoring DSSI synth label:LTS uri: path:/usr/lib/dssi/less_trivial_synth.so duplicate of path:/usr/lib64/dssi/less_trivial_synth.so
Ignoring DSSI synth label:stereo_sampler uri: path:/usr/lib/dssi/trivial_sampler.so duplicate of path:/usr/lib64/dssi/trivial_sampler.so
Ignoring DSSI synth label:mono_sampler uri: path:/usr/lib/dssi/trivial_sampler.so duplicate of path:/usr/lib64/dssi/trivial_sampler.so
Ignoring DSSI synth label:TS uri: path:/usr/lib/dssi/trivial_synth.so duplicate of path:/usr/lib64/dssi/trivial_synth.so
lilv_world_add_plugin(): warning: Duplicate plugin <http://lv2plug.in/plugins/eg-fifths>
lilv_world_add_plugin(): warning: ... found in file:///usr/lib64/lv2/eg-fifths.lv2/
lilv_world_add_plugin(): warning: ... and      file:///usr/lib/lv2/eg-fifths.lv2/ (ignored)
lilv_world_add_plugin(): warning: Duplicate plugin <http://lv2plug.in/plugins/eg-amp>
lilv_world_add_plugin(): warning: ... found in file:///usr/lib64/lv2/eg-amp.lv2/
lilv_world_add_plugin(): warning: ... and      file:///usr/lib/lv2/eg-amp.lv2/ (ignored)
lilv_world_add_plugin(): warning: Duplicate plugin <http://lv2plug.in/plugins/eg-params>
lilv_world_add_plugin(): warning: ... found in file:///usr/lib64/lv2/eg-params.lv2/
lilv_world_add_plugin(): warning: ... and      file:///usr/lib/lv2/eg-params.lv2/ (ignored)
lilv_world_add_plugin(): warning: Duplicate plugin <http://lv2plug.in/plugins/eg-midigate>
lilv_world_add_plugin(): warning: ... found in file:///usr/lib64/lv2/eg-midigate.lv2/
lilv_world_add_plugin(): warning: ... and      file:///usr/lib/lv2/eg-midigate.lv2/ (ignored)
lilv_world_add_plugin(): warning: Duplicate plugin <http://lv2plug.in/plugins/eg-scope#Mono>
lilv_world_add_plugin(): warning: ... found in file:///usr/lib64/lv2/eg-scope.lv2/
lilv_world_add_plugin(): warning: ... and      file:///usr/lib/lv2/eg-scope.lv2/ (ignored)
lilv_world_add_plugin(): warning: Duplicate plugin <http://lv2plug.in/plugins/eg-scope#Stereo>
lilv_world_add_plugin(): warning: ... found in file:///usr/lib64/lv2/eg-scope.lv2/
lilv_world_add_plugin(): warning: ... and      file:///usr/lib/lv2/eg-scope.lv2/ (ignored)
lilv_world_add_plugin(): warning: Duplicate plugin <http://lv2plug.in/plugins/eg-sampler>
lilv_world_add_plugin(): warning: ... found in file:///usr/lib64/lv2/eg-sampler.lv2/
lilv_world_add_plugin(): warning: ... and      file:///usr/lib/lv2/eg-sampler.lv2/ (ignored)
lilv_world_add_plugin(): warning: Duplicate plugin <http://lv2plug.in/plugins/eg-metro>
lilv_world_add_plugin(): warning: ... found in file:///usr/lib64/lv2/eg-metro.lv2/
lilv_world_add_plugin(): warning: ... and      file:///usr/lib/lv2/eg-metro.lv2/ (ignored)
JACK: buffersize changed 256
INFO: Requested timer frequency:1024 actual:1024
Acquired timer frequency: 1024
starting with template /usr/share/muse/templates/default.med
jack connect <MusE:jack-midi-0_out> - <a2j:Midi Through [14] (playback): Midi Through Port-0> failed with err:17
jack connect <a2j:Midi Through [14] (capture): Midi Through Port-0> - <MusE:jack-midi-0_in> failed with err:17
jack connect <MusE:jack-midi-1_out> - <a2j:KRONOS [20] (playback): KRONOS MIDI 1> failed with err:17
jack connect <a2j:KRONOS [20] (capture): KRONOS MIDI 1> - <MusE:jack-midi-1_in> failed with err:17
jack connect <MusE:jack-midi-2_out> - <a2j:MusE [130] (playback): MusE Port 0> failed with err:17
jack connect <a2j:MusE [130] (capture): MusE Port 0> - <MusE:jack-midi-2_in> failed with err:17
INFO: Requested timer frequency:1024 actual:1024

Please let me know if you need other information.

terminator356 commented 3 years ago

Hello. If I understand correctly you are recording midi from the Korg to MusE? If so, hopefully you figured out how to use the Midi Sync Dialog, with its table of sync options. You can accept clock, MMC, realtime commands etc. from any device. It is important to make sure that at least the clock is being accepted - that MusE's transport is being driven from the clock.

Note: In MusE's ChangeLog at 08.09.2020 (See the detailed entry):

So our Global Settings -> Midi tab -> Midi Division (ticks per quarter note drop-down list) was not working well, but should be OK now.

Unfortunately we only had Midi Division entries based on 384 ppq (192, 768 etc.)

But... I just now added some more entries based on 480 ppq (120 - 15360). 480 ppq will be found in the midi division list now. Try from source or daily AppImage.

Tip: Set your desired Midi Division value (480) before recording. Because I think that I do not yet convert existing material whenever Midi Division is changed after recording. It can be done later manually with some of our 'functions' or 'scripts'.

I hope this helps your situation. If I am mistaken and the problem is not with sync but midi file import or export, let me know.

YievCkim commented 3 years ago

Hello

Thanks for your reply.

Actually, I try to record from Muse to Korg. Not from Korg to Muse, but I keep note of this information.

I have configured Muse to send MIDI clock and MIDI real time messages on the midi-out port to the Korg from Muse.

The fact that Muse Midi division is 384ppq is perhaps the origin of my problem.

terminator356 commented 3 years ago

OK Got it. Thanks. Try my new 480 ppq midi division settings anyway. I think our clock output is derived from our midi division setting, so it may actually help in this case.

One drawback is that the division setting is for the whole song. If multiple devices are being driven, they will all get that same division setting, which may not be ideal if different devices use a different ppq. In the future, we could make the division setting per-device/port, so that each device gets its own division setting and MusE does the work of properly scaling event times for each device being driven.

Finally, there is one more caveat: My clock output is not exactly precise for Jack Midi output devices. The clocks are 'bunched together' during each audio cycle. The correct number of clocks are sent, but they are not spaced out properly. Overall timing will be correct but each event might not be precisely timed. There is an issue ticket for that, and I thought I could fix it quickly but it turned out to be far more complicated and I was unable to fix it yet. Clock output for ALSA midi output devices should be OK, and precise. It is only Jack Midi devices which have this problem.

Also, due to an oversight in that same issue report, clock output for ALSA devices only works if Jack Midi is enabled. In other words, if Jack is not running and only ALSA Midi is being used, clock output is not generated. I think it seems to be working for you, so you likely already have Jack running. Hopefully I can fix those issues sometime soon.

Hope that helps. Tim.

YievCkim commented 3 years ago

Thanks. I will try this this weekend. Indeed, I use jack, and I have 2 midi out to Korg one Alsa and one via a2j I will try Alsa.

I need to rebuild muse to.

I will update you soon.

kybos commented 3 years ago

@terminator356

For me changing the ticks per quarter settings seems to change the length of the current session/song/parts/events and everything, not the resolution of the quarter note. Is it a bug or am I missing something? Even for a new session, if you e.g. set the resolution to the max value, you get a new default song with 3 bars only, which suggests that things are calculated based on the number of ticks and not on a dynamic ppq value.

terminator356 commented 3 years ago

For me changing the ticks per quarter settings seems to change the length of the current session/song/parts/events and everything, not the resolution of the quarter note. Is it a bug or am I missing something?

Not a bug, but just current behavior. What was for example a quarter note will then become say, an eighth note. But what we need, and what I think this case needs, is the option to scale all the existing material including song length so that for example a quarter note remains a quarter note. This is the part I have not completed yet - scaling ability whenever the midi division is changed.

This ability is also necessary when loading a song. If the song was recorded with a midi division of say 384, then loaded up while the current midi division is 768, then quarter notes will be eighth notes.

For that reason I recently added a MidiDivision to the song file, it is the global value when the song was last saved. When the song loads, the value is compared with the current value and if the user desires, a scaling action is taken. All TODO actually, as mentioned.

Think of this new midi division song file value as equivalent to the audio sample rate value (which was added 2011). This sample rate value allowed me to compare with the current sample rate and take action by enacting automatic sample rate conversion so that things just work, transparently.

Note that with the midi division or sample rate song file values, if the value is missing from the file because it is too old, a dialog pops up and asks what value to use ie. what he recalls the value was when the song was saved. In the case of sample rate it was relatively easy to suggest a sample rate based on the wave files used in the song, since wave files have a native sample rate. If all the wave files used are 44100Hz, it was very likely the song was created and saved at 44100, which is suggested. No such luck with midi notes. The user will have to remember or guess what the midi division was or leave it on the suggested default (384).

Even for a new session, if you e.g. set the resolution to the max value, you get a new default song with 3 bars only, which suggests that things are calculated based on the number of ticks and not on a dynamic ppq value.

Yes I know, there are some loose ends related to the to-be-done scaling. I took a closer look tonight. The song 'len' value in the template files is stored as ticks. Not to mention any notes and parts etc which are also in ticks. Thus at different midi division values what constitutes a bar is different. The length value found in the templates is supposed to represent 150 bars but here it ends up representing only 3.

An obvious plan for that is to scale everything, as mentioned above regarding song file loading, except here we don't ask questions, we silently scale so that everything just fits and looks the same regardless of midi division.

But I had an idea. For song length, we could be happy rounding off to the nearest bar or the nearest beat - but not tick. Then we could replace that song 'len' value with a 'lenInBars' or 'lenInBeats' value, so that it comes out looking the same always regardless of current midi division value.

I'll see if I can work on some of this stuff over these holidays. Thanks. Sir Talk-a-Lot.

YievCkim commented 3 years ago

Hi,

After build Muse 4 from source, I still have slight differences in events timing when recording Muse to Korg. I have tested several setup (clock via ALSA, via jack, events via jack, via ALSA, several ppq values etc...) The better I get is a slight advance of 4ppq(1.476 instead 2.000 by instance).

I appreciate the new Muse 4 design which looks pretty good anyway. I am going to try this new version in the next days.

Thanks for your help

terminator356 commented 3 years ago

Also, due to an oversight in that same issue report, clock output for ALSA devices only works if Jack Midi is enabled. In other words, if Jack is not running and only ALSA Midi is being used, clock output is not generated.

Sorry that should say: Also, due to an oversight in that same issue report, clock output for Jack devices only works if the 'ALSA' button is clicked. In other words, if Jack midi is running but the 'ALSA' button is not clicked, clock output is not generated.

For more info see my comments at https://github.com/muse-sequencer/muse/issues/661

YievCkim commented 3 years ago

Thank you.

I will look this. I am not at home right now, but I will look this as soon as I am.

YievCkim commented 3 years ago

However I think this is done because If not there is no sync at all. (I am the one which have made the issue 661 too)

YievCkim commented 3 years ago

Hello @terminator356 ,

I have just retried. This is my setup:

in "Midi ports/configuration" dialog Alsa button is selected, in the global settings midi tab dialog RTC clock is set to 2048, and Midi clock to 480ppq,

I have 2 midi alsa output:

and three Midi jack output through a2j:

All of this ports are set by muse at start up (I didn't create them).

I set tc and tr on "jack-midi-0: KRONOS Midi 1" in order to sync the Kronos sequencer to Muse.

I want to record muse output in Kronos sequencer. There is a procedure for this. The Kronos is synced to muse midi clock. I have made 4 measures of midi data in muse in order to test. If I try to record these measures on Kronos (which is synced to muse) the recording works: when I start Muse, the Kronos sequencer start to record the data from Muse and when I stop Muse the Kronos sequencer stop, as expected . BUT, the data are recorded sightly in advance in the Kronos sequencer exactly 14ppq in advance but this shifting seems to increase in time (the last measure for the same note have a 15ppq advance after 4 measures). By instance with a 4/4 metric at 120 bpm, if I have a note which start on the first quarter note on the measure 12 (12.1.0) in Muse the note will be at the measure 11 on 4th quarter note at 466ppq (11.4.466) in Kronos.

I don't know where this shifting comes from and if I can do something to fix that.

YievCkim commented 3 years ago

To make things clearer I have made some screenshots (hope it helps).

First my ports in jack:

jack_graph

then the midi tab in global settings:

muse_midi_settings

the midi ports dialog muse_midi_ports

finally the midi sync setup

muse_midi_clock

github-actions[bot] commented 1 year ago

This issue is stale because it has been inactive for two years. Remove Stale label or write a comment, otherwise it will be closed in 30 days.

github-actions[bot] commented 1 year ago

Issue has been closed automatically after two years of inactivity. Feel free to reopen if the issue is still relevant for current MusE version.