将弯音(MIDI)值转换为“正常”音调值


11

我正在尝试使用此处给出的rt_lpc(实时LPC)实现进行离线LPC分析和综合。该程序中有一些功能可用于脱机LPC分析和综合程序。rt_lpc代码主要用于作曲家等,这意味着它使用MIDI或声门脉冲输入。程序中有一些代码可将音高值(从自相关获得)转换为该bend值。该关系如下所示:

    pitch = (int)( Stk::sampleRate() / midi2pitch[ananya.data[1]] ) /
                            pow( 1.0653f, bend/64.0f*11.0f );
                    power *= ananya.data[2] / 64.0f;
bend = ge.data[1] / 128.0f + ge.data[2] - 64;

有几点:
一。ananya是一个MidiMsg似乎正在动态填充的类型的对象。
b。ge也是一个MidiMsg似乎也在飞行中填充的类型的对象。
C。这两个对象是在程序实时运行时创建的(mine是一个脱机版本,它在我自己的main.cpp中运行它的特定部分。

我的问题:
1.什么是弯音?
2.如何将螺距值转换为折弯值?有哪些映射关系?

我已经用谷歌搜索解决方案,但没有找到明确的答案。

Answers:


12

MIDI的核心是将音乐表示为离散的音符事件,每个音符具有静态音高。这非常适合代表键盘乐器上演奏的音乐。您可以使用以下方式将与回音阶上的音符相对应的任何频率转换为MIDI音符编号:

69+12×log2frequency440

在MIDI接收器校准为A4 = 440 Hz的假设下。

对于钢琴音乐来说,这种表示方式还不错,但是问题是如何表示未映射到调律音阶的音高(非西方音乐,非音乐声音),以及如何表示音符持续时间内的音高变化(glissando,颤音)。

在MIDI中,这是通过使用“音高弯曲消息”来完成的,该消息指示合成器将当前演奏音符的音高偏移一小段时间。默认情况下,大多数合成器会在弯音消息范围(0 .. 16383)的范围内校准+/- 2个半音。8192对应于没有音高弯曲-发出的音高恰好是音符值的音高。弯音值与移频比之间的映射关系为:

femitted_notefnote_message=2pitchbend81924096×12

因此,您可以从以下公式获得合成器演奏的音符的频率:

440×2note6912.0+pitchbend81924096×12

其中note是最后收到的Note On消息的7位MIDI音符编号;和弯音是最后接收到的14位值弯音消息。合成器首先将其弯音寄存器设置为8192,并且在接收“重置所有控制器”消息期间也将重置该值。

让我们来看下面的例子。您想要用以下频率轨迹表示长笛颤音:500 Hz,510 Hz,500 Hz,作为MIDI信息。

基符编号为:

round(69+12×log2(500/440))=71

因此,您发送一条“ note on”消息,其note#等于71。这等于音高为:

440×2(7169)/12=493.88

这是回火刻度上最接近的音高。您需要发送弯音消息以将音调提高以下倍数:

500493.88=1.0124

并获得500 Hz。相应的弯音值为:

[RØüñd8192+4096×12×ØG21.0124=9065

要获得510 Hz,弯音值应为:

[RØüñd8192+4096×12×ØG2510493.88=10469

因此,对于500、510、500 Hz,您的MIDI消息序列为:

  • 注71
  • 弯音9065
  • ...
  • 弯音10469
  • ...
  • 弯音9065

您可以将MIDI音符编号视为音高的“不可分割”部分。且音高弯曲是音高的多余“小数”部分。


另外,从我对代码的理解来看,ge是弯音消息;ge.data [2]的MSB和ge.data [1]的LSB。ananya是消息上的注释,ananya.data [1]是注释编号,ananya.data [2]是速度。除了时髦的变量命名似乎暗示着代码作者之间隐藏的浪漫外,我在这里还看到了潜在的WTF:1.0653f和11.0f常量有些麻烦。可读的选择是:1.05946f和12.0f。或1.06504f和11.0f。作者似乎假设音高弯曲范围为+/- 1个八度,这是另一个潜在的WTF。
pichenettes 2012年

ROTFL上的“隐藏的浪漫”部分!我认为我没有正确地理解这一点,所以请多多包涵。音高值是从函数获取的,在autocorrelate我看来,这就像是输出的MIDI Note。注意midi2pitch公式中的数组吗?如果我是对的,那意味着我仍然没有bend音高的值或实际值来估计弯曲值,除非我有MIDI文件,否则也无法获得它们。一个简单的例子,变量太多,方程太少。velocity在这种情况下,如何估算弯曲度,实际螺距值和?
Sriram'3

你想做什么?将音高/功率对转换为MIDI消息?还是将MIDI数据转换为实际音高?上面给出的代码将一对传入的MIDI音符+弯音消息(ananya msg,ge msg)转换为句点(音高变量)和功率(功率变量)。我认为这是用MIDI键盘控制的合成音源代替LPC激励-一种粗糙的声码器或自动调谐效果。
pichenettes 2012年

快速浏览rt_lpc.cpp确认输入的0xe0类型的MIDI消息(PITCH BEND)正在更新弯音值;并将输入的0x90类型MIDI消息(NOTE ON)复制到“ ananya”消息中。从那里开始,使用这些值完成使用修改音高的重新合成。不确定您要从那里做什么。
pichenettes 2012年

1
是的,对于创意信号转换,MIDI输入是完全不同的东西。它不是常规LPC分析/综合链的一部分; 而是允许从键盘读取某些参数(音高和功率),而不是由分析模块产生这些参数。也许您可以提出一些带有音频文件示例的新问题,并提取以Hz为单位的音高轨迹,以便我们将您定向到更可靠的音高估计技术。Aubio库中有一些音高跟踪器的变体。
pichenettes 2012年

6

MIDI是一种协议,它允许(主要)合成器控制其他合成器或计算机或由其他合成器或计算机控制。

它是一个串行协议,允许交换消息,例如“ C1向上键”,“ D4向下键”,“力度”,“音调变化”等。许多控制器都有一个“音调轮”,它是操纵杆或调幅轮。播放器以交互方式更改当前弹奏音符的音高以手动创建颤音或连续从一个音符“变滑”到另一个音符,这通常是吉他演奏者通过用左手弯曲琴弦来完成的,通常称为弯音,因此得名。

MIDI音高弯曲消息是一种传达在任何给定时间点应该发生多少音高变化的方式。接收到音高弯曲消息的合成器(软件或硬件)应该将给定数量的所有当前音符的音高改变。

控制器消息的自变量从-8192到8191,在标准MIDI文件中,它应覆盖-200分到200分的范围,其中1分是半音的1/100,即比率2 ^( 1/1200)= 1.000577789506555。示例:要创建向下的音调偏移以达到标称频率的93%,则控制器值为

c = round(log2(.93)*12*8192/2);

或-5146(在这种情况下)。0.93是您想要的比率,12个八度音阶的半音数,2个最大音高弯曲范围(在这种情况下为200美分或2个半音),以及log2()以2为底的对数。

但是,在大多数合成器中,该范围是可配置的,并且假定所有合成器的行为均相同可能不是一个好主意。

这是一个可能有用的转换表。 http://www.elvenminstrel.com/music/tuning/reference/pitchbends.shtml

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.