JavaScript 音序器 MIDI 文件时序分辨率 (PPQN)

JCs*_*Css 7 javascript midi web-midi

我阅读了很多关于 MIDI 分辨率的内容,并研究了一些代码,如 Tone.js 和 heartbeat。但我不明白为什么会有不同的每季度音符 (PPQN)值以及它对演奏音符的影响。当我有 960 PPQN 时,这意味着 1 个四分音符有 960 个刻度,1 个八分音符 480 个刻度,等等。如果我理解正确,增量时间只是一个相对值。

我不明白的是,当我在 JavScript 中演奏音符时,PPQN 应该是什么,以及当我设置 PPQN 时为什么它应该具有这个值?例如,我使用 WebAudio API 来播放音符:

function nextNote() {
  var quarterBeat = 60.0/tempo;
  nextNoteDuration = nextNoteDuration + (quarterBeat/32);
  currentNote++;
}
Run Code Online (Sandbox Code Playgroud)

这样我就可以演奏不同的音符时长。现在,当我读取 MIDI 文件时,是否应该只比较增量时间并将其转换为我的音序器当前播放?例如,当我读取具有以下值的 MIDI 文件时:

Tempo = 120
PQN = 960
4 Quarter Notes
Run Code Online (Sandbox Code Playgroud)

我读取了 MIDI 文件,将音符保存在一个数组中(假设每个音符的增量时间为 1/4)

duration = [quarterNote, quarterNote, quarterNote, quarterNote]
Run Code Online (Sandbox Code Playgroud)

并演奏音符:

while (nextNoteDuration < audioContext.currentTime) {
  if (duration[i] %32 == 0) playNote(currentNote, nextNoteDuration);
  nextNote();
  i++;
}
Run Code Online (Sandbox Code Playgroud)

我应该只在导出 MIDI 文件时使用 PPQN 吗?如果是这样,我应该如何设置 PPQN?我希望有人能更详细地向我解释这一点。

For*_*tor 1

PPQ 与分辨率有关。更具体地说是关于时间分辨率。

当我在 JavScript 中演奏音符时,PPQN 应该(是什么?)是什么?当我设置 PPQN 时,为什么它应该具有这个值?

当您的程序播放音符时,它可以使用您想要或需要的任何时间单位,例如毫秒、纳秒、电影帧、滴答声。绝对挂钟或相对时间。这取决于您的音序器功能和软件功能。仅当将 MIDI 序列存储为 MIDI 文件时才需要选择 PPQ 值。当然,您需要能够在读取/存储 MIDI 文件时转换时间单位。

现在,当我读取 MIDI 文件时,我应该比较增量时间并将其转换为我的音序器当前播放吗?

当然,如果您的音乐事件在内部使用不同的时间表示形式,那么您需要能够将增量时间从 MIDI 文件转换为您的内部表示形式。

您只询问 PPQ,但该值仅在 MIDI 文件头中找到一次。相反,速度事件可能会在文件中多次发生,并且它会影响下一个增量时间到挂钟时间的转换,直到下一个速度事件。如果您的音序器/播放器允许用户更改/添加节奏事件,则最好使用相对单位而不是挂钟单位来表示内部时间(或两者)。

我应该仅在导出 MIDI 文件时使用 PPQN 吗?如果是这样,我应该设置什么 PPQN?

是的,导出 MIDI 文件时需要为 PPQ 选择合适的值。如果您的内部时间单位是相对的(就像大多数音序器那样),则使用 PPQ 的内部单位分辨率。如果您从挂钟单位转换为增量时间,那么您需要选择一个分辨率,使您的翻译丢失较少的细节(通过量化)。从这个意义上说,值越高越好。Rosegarden始终使用 960 PPQ 存储 MIDI 文件。相比之下,Steinberg 的Cubase使用的是 480。我记得很久以前使用 Cakewalk 时只有 120 PPQ,但后来的版本允许将此值作为配置设置进行更改。一般来说,您不仅需要适应所有短于四分之一的音乐人物,包括三连音等细分,而且还需要考虑基于精细时间调整的摇摆等效果。