【问题标题】:get frenquencies in Processing with Minim使用 Minim 在处理中获取频率
【发布时间】:2012-04-26 17:31:57
【问题描述】:

我尝试使用处理从麦克风获取频率。我混合了文档中的两个示例,但“最高”并不是真正的赫兹(a 是 440 赫兹)。 你知道如何拥有比这更好的东西吗?

import ddf.minim.*;
import ddf.minim.analysis.*;

Minim minim;
AudioInput in;
FFT fft;
int highest=0;

void setup()
{
  size(1024, 200, P2D);

  minim = new Minim(this);
  minim.debugOn();

  in = minim.getLineIn(Minim.MONO, 4096, 44100);
  fft = new FFT(in.left.size(), 44100);
}

void draw()
{


  background(0);
  stroke(255);

  fft.forward(in.left);
  highest=0;
  for (int n = 0; n < fft.specSize(); n++) {
    // draw the line for frequency band n, scaling it by 4 so we can see it a bit better
    line(n/4, height, n/4, height - fft.getBand(n)*4);

    //find frequency with highest amplitude
    if (fft.getBand(n)>fft.getBand(highest))
      highest=n;
  }
  println(highest);

  //println(fft.getFreq(110));
  // draw the waveforms
  for (int i = 0; i < in.bufferSize() - 1; i++)
  {
    line(i, 50 + in.left.get(i)*50, i+1, 50 + in.left.get(i+1)*50);
    line(i, 150 + in.right.get(i)*50, i+1, 150 + in.right.get(i+1)*50);
  }
}


void stop()
{
  // always close Minim audio classes when you are done with them
  in.close();
  minim.stop();

  super.stop();
}

【问题讨论】:

    标签: processing minim


    【解决方案1】:

    你需要做一些转换,这取决于你想要得到什么:

    频谱并不代表单个频率,而是实际上代表以特定频率为中心的频带。每个频段的中心频率通常表示为时域信号采样率的分数,等于频段索引除以频段总数。频带的总数通常等于时域信号的长度,但仅对索引小于一半长度的频带提供访问,因为它们对应于低于奈奎斯特频率的频率。换句话说,给定一个长度为 N 的信号,频谱中会有 N/2 个频段。

    例如,如果您构造一个 timeSize 为 1024 的 FFT,并且 44100 Hz 的采样率,则频谱将包含以下值 频率低于 22010 Hz,这是奈奎斯特频率(一半 采样率)。如果您要求带编号 5 的值,这将 对应于以 5/1024 * 44100 = 为中心的频带 0.0048828125 * 44100 = 215 赫兹。该频带的宽度等于 2/1024,表示为总带宽的一部分 光谱。频谱的总带宽等于奈奎斯特 频率,在本例中为 22100,因此带宽等于 约 50 赫兹。你没有必要记住所有这些 关系,尽管了解它们是件好事。获取频率 允许您查询频率为 Hz 的频谱和方法 getBandWidth 将返回以 Hz 为单位的每个频带的带宽 光谱。

    来自Minim Manual, FFT section

    【讨论】:

    • 有点抽象……我想在乐器上弹奏单个音符时以 Hz 为单位获得值……我不知道为什么手册中没有简单的示例。如果你知道我可以在哪里改进我的代码,很高兴分享它。
    • 这解释了您感兴趣的位 - 赫兹转换:如果您要求频带编号 5 的值,这将对应于以 5/1024 * 44100 = 为中心的频带0.0048828125 * 44100 = 215 Hz。在您的代码中,您使用 getBand(),文档指出:返回请求频带的幅度。您可能想尝试 getFreq (float freq)(例如 fft.getFreq(440)) 获取频谱中请求频率 (Hz) 的幅度
    • 我想我理解为什么我有点麻烦,使用 int 来获得最高的返回不精确值(我会再试一次并在将来发布我的代码)。谢谢你的回答!
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-05-02
    • 1970-01-01
    • 2012-12-25
    • 1970-01-01
    • 2021-09-13
    相关资源
    最近更新 更多