FHT to frequency

Moderator: guest

Forum rules
Due to heavy spam, new user registration has been disabled. Hundreds of posts from this sub-forum were accidentally lost in the pruning process.

FHT to frequency

Postby jbolfiil » Tue Jan 20, 2015 5:35 pm

Hello,

I am trying to get the FHT converted to frequency. I saw that the formula was k*(samples/FHT_N) but I can't seem to get what I want...

1. Does k need to be unsigned? I am getting negative values when ever I try to print it out to the serial monitor.

2. How do you find out what the sampling rate is? I have read that you need to look at the prescalar but I am not sure what that is.

I am just trying to write a high on a digital pin when a certain frequency is present. Any help will be appreciated!

Also, will I need to set a magnitude threshold somehow? I only want the high on the digital pin when there is an intentional sound.

(I just realized that I did not bias the signal so that maybe a cause for off numbers.)
jbolfiil
 
Posts: 5
Joined: Mon Jan 19, 2015 5:31 pm

Re: FHT to frequency

Postby guest » Tue Jan 20, 2015 9:14 pm

so to figure out which bin relates to what frequency, you need to know the sample rate. if you are using the default example from the library, that is 38kHz.

Frequency(k) = (k)*(sample_rate)/(FHT_N)

k is just the bin number.

if you want a pin to go high based on a certain frequency, just figure out which bin that is, and then check the value in that bin compared to a threshold, and set the pin high if its above the threshold
guest
Site Admin
 
Posts: 449
Joined: Thu May 20, 2010 11:58 pm

Re: FHT to frequency

Postby jbolfiil » Wed Jan 21, 2015 11:01 am

How can I change the sampling rate? I this is how it works...If I increase the sampling rate, the smaller the bin size will be and the more accurate the signal is represented right? But doing that will slow the transformation right?

So if I simply put:

Code: Select all
frequency = (k)*(38000/FHT_N);
Serial.print(frequency);


inside the For loop but outside the While loop, I will get the frequency to display on the monitor?

Could you give me an example of how I would detect the bin that contains the frequency I want to detect?
jbolfiil
 
Posts: 5
Joined: Mon Jan 19, 2015 5:31 pm

Re: FHT to frequency

Postby guest » Wed Jan 21, 2015 2:01 pm

1. no, increasing the sampling rate increases the bin size: bin size = sample rate / FHT_N
2. it also changes the maximum frequency you can detect: max freq = samplerate / 2
3. your code should print the frequency correctly
4. im not sure what your asking here:
Could you give me an example of how I would detect the bin that contains the frequency I want to detect?


do you know what frequency you are interested in?
guest
Site Admin
 
Posts: 449
Joined: Thu May 20, 2010 11:58 pm

Re: FHT to frequency

Postby jbolfiil » Wed Jan 21, 2015 8:40 pm

guest wrote:do you know what frequency you are interested in?


I was interested in around 4kHz. But I also want to experiment will other frequencies.

guest wrote:im not sure what your asking here:
"Could you give me an example of how I would detect the bin that contains the frequency I want to detect?"


Sorry, it was a little confusing! I just wanted to write a digital high on a pin once a frequency is present. So in order to do this, I need to wait until a specified bin reaches above a threshold... (I think?)

Pseudocode:

Code: Select all
if(bin #155 > some magnitude)
{
digital.Write(Pin2, HIGH);
}
(



Would something like this work? If so, how do I specify the bin number and the magnitude in code?
jbolfiil
 
Posts: 5
Joined: Mon Jan 19, 2015 5:31 pm

Re: FHT to frequency

Postby guest » Thu Jan 22, 2015 12:04 am

yes, after you calculate the bin from the formula, then you grab it and check it each time through. dont forget to reset it if its not greater than a certain level.

this will check bin 27:
Code: Select all
if (fht_log_out[27] > 100) {
  set pin high
}
else {
  set pin low
}
guest
Site Admin
 
Posts: 449
Joined: Thu May 20, 2010 11:58 pm

Re: FHT to frequency

Postby jbolfiil » Fri Jan 23, 2015 4:06 pm

For some reason, I cannot get the frequency to print out.

here is the code

Code: Select all
/*
fht_adc.pde
guest openmusiclabs.com 9.5.12
example sketch for testing the fht library.
it takes in data on ADC0 (Analog0) and processes them
with the fht. the data is sent out over the serial
port at 115.2kb.  there is a pure data patch for
visualizing the data.
*/

#define LOG_OUT 1 // use the log output function
#define FHT_N 256 // set to 256 point fht

#include <FHT.h> // include the library

int k;
int frequency;

void setup() {
  Serial.begin(115200); // use the serial port
  TIMSK0 = 0; // turn off timer0 for lower jitter
  ADCSRA = 0xe5; // set the adc to free running mode
  ADMUX = 0x40; // use adc0
  DIDR0 = 0x01; // turn off the digital input for adc0
}

void loop() {
  while(1) { // reduces jitter
    cli();  // UDRE interrupt slows this way down on arduino1.0
    for (int i = 0 ; i < FHT_N ; i++) { // save 256 samples
      while(!(ADCSRA & 0x10)); // wait for adc to be ready
      ADCSRA = 0xf5; // restart adc
      byte m = ADCL; // fetch adc data
      byte j = ADCH;
      k = (j << 8) | m; // form into an int
      k -= 0x0200; // form into a signed int
      k <<= 6; // form into a 16b signed int
      fht_input[i] = k; // put real data into bins
    }
    fht_window(); // window the data for better frequency response
    fht_reorder(); // reorder the data before doing the fht
    fht_run(); // process the data in the fht
    fht_mag_log(); // take the output of the fht
    sei();
   
    frequency = (k)*(38000/FHT_N);
    Serial.println(frequency);
   
    //Serial.write(255); // send a start byte
    //Serial.write(fht_log_out, FHT_N/2); // send out the data
  }
}


All I did was declare k and frequency globally and then inserted this:

Code: Select all
   
frequency = (k)*(38000/FHT_N);
Serial.println(frequency);


I am getting random and some negative numbers in the monitor...
When I just display "k," I am getting numbers from -64 to 128. I don't think the bin number are supposed to be negative.

Even when the signal is not attached, it is just spitting out values. Is there something I'm missing?
jbolfiil
 
Posts: 5
Joined: Mon Jan 19, 2015 5:31 pm

Re: FHT to frequency

Postby guest » Fri Jan 23, 2015 4:17 pm

you are using k twice, for 2 different purposes:

Code: Select all
      k = (j << 8) | m; // form into an int
      k -= 0x0200; // form into a signed int
      k <<= 6; // form into a 16b signed int
      fht_input[i] = k; // put real data into bins


and you never assign k a value for your frequency operation. at the beginning, declare it like this (instead of using k):

Code: Select all
int bin = 7; // whatever bin youre interested in
guest
Site Admin
 
Posts: 449
Joined: Thu May 20, 2010 11:58 pm

Re: FHT to frequency

Postby jbolfiil » Sat Jan 24, 2015 12:37 pm

guest wrote:you are using k twice, for 2 different purposes:
Code: Select all
      k = (j << 8) | m; // form into an int
      k -= 0x0200; // form into a signed int
      k <<= 6; // form into a 16b signed int
      fht_input[i] = k; // put real data into bins



well I just kept that the same... I didn't think I had to mess with that.

For right now, I just want to display the frequency on the serial port. I will worry about detecting a certain bin a little later on. You might have to just write down the necessary changes and spell it out for me since I am not getting it! Sorry about all the trouble!
jbolfiil
 
Posts: 5
Joined: Mon Jan 19, 2015 5:31 pm

Re: FHT to frequency

Postby guest » Sat Jan 24, 2015 9:42 pm

well, you could try something like this:

Code: Select all
for (byte i = 0 ; i < FHT_N/2 ; i++) {
  Serial.print(i*38000/FHT_N);
  Serial.print(" = ");
  Serial.println(fht_log_out[i]); // send out the data
}
guest
Site Admin
 
Posts: 449
Joined: Thu May 20, 2010 11:58 pm


Return to General

Who is online

Users browsing this forum: No registered users and 1 guest


cron