2011-10-12 37 views
7

Tôi có trình phát âm thanh sử dụng NAudio và tôi muốn hiển thị cường độ thời gian thực cho mỗi băng tần.Cường độ dải tần số âm thanh

tôi có một sự kiện được kích hoạt cho mỗi khối 1024 mẫu:

public void Update(Complex[] fftResults) 
{ 
    // ?? 
} 

gì tôi muốn có là một mảng các số cho thấy cường độ của mỗi băng tần. Cho phép nói rằng tôi muốn chia cửa sổ thành 16 dải.

Ví dụ khi có nhiều nhịp bass nó có thể trông như thế này:

░░░░░░░░░░░░░░░░ 
▓▓▓░░░░░░░░░░░░░ 
▓▓▓░░░░░░░░░░░░░ 
▓▓▓▓░░░░░░░░░░░░ 
▓▓▓▓▓░░░░░░░░░░░ 
▓▓▓▓▓▓▓▓░░░▓░░▓░ 

tôi nên đặt gì vào đó xử lý sự kiện nếu điều này là có thể với dữ liệu đó?

Dữ liệu đến (Phức tạp []) đã được chuyển đổi bằng FFT. Đây là luồng âm thanh nổi.

Trước tiên hãy thử:

double[] bandIntensity = new double[16] { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }; 

    public void Update(Complex[] fftResults) 
    { 
     // using half fftResults because the others are just mirrored 
     int band = 0; 
     for (int n = 0; n < fftResults.Length/2; n++) 
     { 
      band = (int)((double)n/(fftResults.Length/2) * bandIntensity.Length); 
      bandIntensity[band] += Math.Sqrt(fftResults[n].X * fftResults[n].X + fftResults[n].Y * fftResults[n].Y); 
      bandIntensity[band] /= 2; 
     } 
    } 

Trên đây là làm cái gì nhưng tôi nghĩ quá nhiều đi vào hai ban nhạc đầu tiên, và tôi đang chơi shakira mà không có nhiều âm bass.

Cảm ơn!

Trả lời

8

Có hai vấn đề riêng biệt mà bạn có thể muốn giải quyết ở đây:

(1) Chức năng Window

Bạn cần phải áp dụng một window function để dữ liệu của bạn trước khi FFT, nếu không bạn sẽ nhận được spectral leakage mà sẽ tạo ra một quang phổ rất bị bôi nhọ. Một hiệu ứng phụ khó chịu của rò rỉ quang phổ là nếu bạn có bất kỳ loại thành phần DC (0 Hz) quan trọng nào thì điều này sẽ dẫn đến loại hình 1/f mà bạn nhìn thấy trên biểu đồ thanh của bạn.

(2) Đăng nhập biên độ/tần số trục

thính giác của con người là bản chất logarit trong cả cường độ lẫn tần số trục. Không chỉ vậy, nhưng lời nói và âm nhạc có xu hướng có nhiều năng lượng hơn trong phần tần số thấp hơn của quang phổ. Để có được hiển thị dễ dàng hơn và có ý nghĩa hơn về cường độ so với tần số, chúng ta thường tạo cả độ lớn và trục tần số lôgarit. Trong trường hợp mức độ trục này thường được đưa về chăm sóc bằng cách vẽ dB tái quy mô đầy đủ, tức là

magnitude_dB = 10 * log10(magnitude); 

trong trường hợp tần số trục có thể bạn sẽ muốn nhóm thùng của bạn vào ban nhạc, mà mỗi có thể một quãng tám (dải tần số 2: 1), hoặc phổ biến hơn cho độ phân giải cao hơn, quãng tám thứ ba. Vì vậy, nếu bạn chỉ muốn 10 "thanh" thì bạn có thể sử dụng các ban nhạc quãng tám sau:

25 - 50 Hz 
    50 - 100 Hz 
    100 - 200 Hz 
    200 - 400 Hz 
    400 - 800 Hz 
    800 - 1600 Hz 
1600 - 3200 Hz 
3200 - 6400 Hz 
6400 - 12800 Hz 
12800 - 20000 Hz 

(giả sử bạn có một tỷ lệ mẫu 44,1 kHz và một giới hạn trên phần cứng đầu vào âm thanh của bạn là 20 kHz).Lưu ý rằng trong khi có quy mô cường độ cường độ (dB) là khá bắt buộc đối với loại ứng dụng này, trục tần số log ít quan trọng hơn, vì vậy bạn có thể thử binning tuyến tính hiện tại và chỉ xem hiệu ứng nào bạn nhận được từ việc áp dụng một chức năng cửa sổ trong miền thời gian (giả sử bạn chưa có) và chuyển đổi tỷ lệ độ lớn thành dB.

+1

bạn là anh hùng của tôi. lol. –

+0

Đối với cửa sổ tôi thấy rằng BlackmannHarrisWindow được sử dụng. Tuy nhiên tôi đã không thử 10xLog10() được nêu ra, tôi sẽ thấy làm thế nào mà thay đổi đồ thị. Và tôi sẽ tháo thùng DC 0Hz. –

+0

ngay cả sau khi áp dụng một thùng octave để thu thập ban nhạc, tôi vẫn nhận được số lạ, vẫn còn quá nhiều ở phía bên trái ... tôi đã chuyển đổi các số tỷ lệ y thành dBs –

Các vấn đề liên quan