Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Feature request: Musical spectrum mode (display frequency/notes on the x-axis) #289

Open
tecosaur opened this issue Dec 3, 2019 · 13 comments

Comments

@tecosaur
Copy link

tecosaur commented Dec 3, 2019

Hello,

I'm here from foobar2k + foo_musical_spectrum on windows. For the most part this does a fantastic job but there's something I really miss.

I found that fb2k + musical spectrum having the bins at each semitone worked particularly well for 'watching my music'.

image

Something that I imagine wouldn't be too much work, but would be very nice, is to add a "Music mode" in config which I envision as operating a bit like so:

[musical]

# whether to use 'musical' mode. This overrides bars, lower_cutoff_freq, and higher_cutoff_freq
; enabled = false

# the range of notes to create bars for (every semitone inbetween, inclusive)
; lowest_note = A1
; hightest_note = C9

; min_volume_dbfs = -60
; max_volume_dbfs = 0

; peaks = true
# how long to hold peak for, in ms
; peak_hold = 500
# Gravity in db/s^2
; peak_gravity = 50

I imagine an end result like this

 -20dB                                                                                    ▃
                                                                ▅                         █
                                                                █                       ▁ █
                                                                █                       ▁ █
                                                                █                       █ █
                                                                █                       █ █
 -30dB                                                          █                       █ █              	
                                                                █ ▅                     █ █ ▁
                                                                █ █                     █ █
                                                                █ █                     █ █ ▃
                                                                █ █                     █ █ █
                                                                █ █                     █ █ █            	
 -40dB                                                          █ █                     █ █ █       ▁     ▁     ▇                     ▂	        ▄ ▆
                                                    ▁           █ █                     █ █ █             █     █                     █         █ █
                                                              ▃ █ █                     █ █ █       ▁     █ ▃   █         ▃     ▅     █         █ █ ▅
                                                              █ █ █                     █ █ █       █     █ █   █ ▄       █ ▄   █     █     ▃   █ █ █
                                                              █ █ █                   ▇ █ █ █       █     █ █   █ █       █ █   █ ▃   █   ▄ █ ▄ █ █ █
                                                              █ █ █                   █ █ █ █       █   ▄ █ █   █ █     ▃ █ █   █ █ █ █ ▁ █ █ █ █ █ █ ▆
 -50dB          ▁                                     ▁       █ █ █                 ▆ █ █ █ █ ▁     █   █ █ █   █ █ ▃   █ █ █ ▇ █ █ █ █ █ █ █ █ █ █ █ █
              ▁   ▁                                           █ █ █           ▁ ▁   █ █ █ █ █ █ ▁   █   █ █ █ ▆ █ █ █   █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █
                ▄	▁ ▁               ▁                 ▁ █ █ █ ▅         █ █ ▆ █ █ █ █ █ █ █   █ ▄ █ █ █ █ █ █ █   █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █
              █ █       ▁           ▁             ▁ ▄       ▂ █ █ █ █         █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █
              █ █   ▄ ▁ ▇ ▁         ▆   ▃   ▅       █   ▆ ▄ █ █ █ █ █ ▅   ▃ ▇ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █
            ▁ █ █ ▂ █ █ █   ▁ ▃   ▂ █ ▂ █   █   ▂ ▆ █ █ █ █ █ █ █ █ █ █ ▅ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █
 -60dB  ▁ ▂ ▆ █ █ █ █ █ █ ▂ ▇ █ █ █ █ █ █ ▁ █ ▆ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █ █
        A   B C1  D   E F   G   A   B C2  D   E F   G   A   B C3  D   E F   G   A   B C4  D   E F   G   A   B C5  D   E F   G   A   B C6  D   E F   G   

Better low-frequency resolution would also be nice, but that's being discussed in #268

Thanks!

tecosaur

@karlstav
Copy link
Owner

karlstav commented Jan 4, 2020

hi @tecosaur and sorry for the late reply. To print the frequency on the x-axis has actually been on the todo list for over two years! To be able to have notes instead of frequency would then of course be an easy implementation. So I will get around to this some time soon, hopefully.

Peaks on the other hand is a bit tricky due to the 1/8 -7/8 blocks that cava use to increase resolution on the terminal: https://www.unicode.org/charts/PDF/U2580.pdf

I would need horizontal line characters that would range from top to bottom in height position with 1/8 intervals and I don't know if they exist.

Also I am not sure how useful a dB scale would be as there is a lot of EQing and filtering to make the bars look nice. I could off course have an option to turn off all filters, there actually used to be, but I removed it a while back.

@tecosaur
Copy link
Author

tecosaur commented Jan 4, 2020

@karlstav no problem, we all get busy 😄.

It's great to hear that frequency on the X-axis is on the near-term todo list. As you say, having notes from that wouldn't bee to hard. Do you have any thoughts on supporting a note-based frequency range as in the example? I know I'd find it much easier to work with that looking up the frequency of notes, and it should be fairly easy to implement.

For peaks, unfortunately, I don't think it's going to be possible to get the same resolution as you said, but I think we can at least do better than 1 block/link with ▁━▔. If this is possible to add, I think would be rather nice for short-lived spikes such as those from percussion, and the trade-off in resolution shouldn't be too bad.

With a dB scale, I assumed that cava just worked by:

  • scrape audio from pulse/alsa
  • run through FFT
  • visualise

What more happens?

@karlstav
Copy link
Owner

karlstav commented Jan 5, 2020

Do you have any thoughts on supporting a note-based frequency range as in the example?

That wouldn't be a problem.

I think we can at least do better than 1 block/link with ▁━▔.

you are right, I'll test it when I get time

What more happens?

First there is an EQ calculated around here:

cava/cava.c

Line 648 in 8ecdf48

k[n] = pow(fc[n], 1);

The mathematics in the code should have been formatted in a clearer way. Right now it looks sort of messy (power of one!? what?) But what it generally does is to amplifying the higher frequencies. If not we would only have seen the bass and not much more.

there is also the gravity (falloff) and integral filter made to make cava look smoother, but not necessarily be a precise representation of the audio.

@karlstav karlstav changed the title Feature request: Musical spectrum mode Feature request: Musical spectrum mode (display frequency/notes on the x-axis) Aug 26, 2020
karlstav added a commit that referenced this issue Sep 7, 2020
only added frequency for now, will look at notes later

also fixed some bugs in the frequency calculation, the "push spectrum
if clumped" where causing too high frequencies to still use the bass
buffers. There was also a +1 too many causing bars to be one off
compared to the calculated frequency.
@neagle
Copy link

neagle commented Feb 28, 2021

I just wanted to check in to see what the status of this was: I'd love to have an option that maps frequency to the x-axis, as I'd like to map different pitches to different areas of my display: deeper notes to one part, higher notes to another.

@karlstav
Copy link
Owner

karlstav commented Mar 1, 2021

@neagle as you can se I added config option: x-axis scale (frequency) some time back:

9c0c414

mapping "different pitches to different areas" complicates things a bit, not really sure about the use case either. Now it's lower to higher left to right, or mirrored outwards from center if stereo. I could off course add an option to reverse it if it's mono. But to arbitrarily have this range here and that range there sounds a bit strange.

@neagle
Copy link

neagle commented Mar 1, 2021

I should have added some more detail: I tried adding XAXIS = FREQUENCY to my config based on that commit, but then I got no bar movement when I tried running CAVA. Since I didn't see any additions to the documentation regarding the feature, I wasn't sure if it was completed work, yet, or if I might be doing something wrong.

mapping "different pitches to different areas" complicates things a bit, not really sure about the use case either.

I may be unintentionally making my use-case sound more complicated than it is. All I was hoping to find was a way to have it be lower to higher left to right, as you said. But I didn't understand that apparently it already is that, and that what is confusing me is apparently the mirroring outwards from center when it's stereo. Now that you've explained that, I was able to find that explanation in the config file. Switching it to mono should do exactly what I want. Sorry for my confusion, but thanks for the helpful response!

@karlstav
Copy link
Owner

karlstav commented Mar 1, 2021

no problem @neagle !

the xaxis config option is not very well tested, but I thought it should work. It is case sensitive and should be lower case. did you really write it in upper case in the config?

@neagle
Copy link

neagle commented Mar 1, 2021

Heh, I did*. Now that I look a little more closely, spurred by your comment, I can see why it should be lowercase. I'll look forward to giving it a try when I get home this evening.

*Actually, scratch that—I'm not sure. I'm at work right now so I can't check the files on my rPi.

@bunder2015
Copy link

bunder2015 commented May 1, 2022

Hello, I am new to cava but thought I would give this a try... although I seem to have some weird effect with the bar ranges...

image

It seems that the last bar is misprinted or has the wrong frequency range. I haven't yet tested if that's a misprint or if the bar is actually the wrong frequency range. I want to file a separate issue for the bars though because I have some questions about the ranges for each bar when playing back single frequency sounds.

In the meantime, here is the config I am using:

[general]
bars = 45
bar_width = 4

lower_cutoff_freq = 19 # if i use 20 the bars start at 21 or 23 or something
higher_cutoff_freq = 20000

[output]
channels = mono

xaxis = frequency

[color]
background = '#000000'
foreground = '#00ff00'

gradient = 1
gradient_count = 8
gradient_color_1 = '#00aa00'
gradient_color_2 = '#00ff00'
gradient_color_3 = '#00ff00'
gradient_color_4 = '#00ff00'
gradient_color_5 = '#ffff00'
gradient_color_6 = '#ffff00'
gradient_color_7 = '#ff0000'
gradient_color_8 = '#ff0000'

edit: I had a poke around with audacity's tone generator, and the last bar seems to be around 17.1khz.

karlstav added a commit that referenced this issue May 1, 2022
@karlstav
Copy link
Owner

karlstav commented May 1, 2022

hi @bunder2015,

i forgot to test this feature after moving some code around recently. there was indeed an ugly bug where the last upper cut off was just hard coded to 10k. There was also a bug where the bars weren't labels correctly in stereo output mode. Both are fixed now. Regarding the range, the label is simply the center frequency per bar calculated like this:

sqrt(lower cut off * higher cut off)

@bunder2015
Copy link

bunder2015 commented May 1, 2022

Oh cool, thanks for getting back to me. I tried your patch and it seems to fix the last bar text. Thanks!

The reason I asked about the bar ranges is that I like to listen to music with a lot of sub-bass frequencies. When I was playing with audacity's tone generator or listening to test tracks I was getting stuff like this:

60hz
Screenshot at 2022-05-01 06-31-54

35hz
Screenshot at 2022-05-01 06-37-22

60hz and 120hz at the same time, with the same volume (not sure what's up with that stray 178 bar)
Screenshot at 2022-05-01 07-21-10

I'm guessing the 4-5 wide bar response is only visible at lower frequencies, when I looked at the other end of the scale it only happened in a small crossover range between the two bars.

Thanks again

@karlstav
Copy link
Owner

karlstav commented May 1, 2022

No problem.

This is due to the limited size of the audio input buffer. The "resolution" will become better at the low end if we use a larger input buffer, but that would the visualization slower.

The stray bump is because the signals are out og phase. So you would get a third signal at 60 + 120 Hz

@bunder2015
Copy link

Ah that makes sense, I didn't check whether audacity was generating them on the same cycle.

I still have some more questions about the buffer, but I'll ask them in a new issue (I promise this time 😄)

While I'm here though, one thing I did notice was that the bar text is printed using the highest gradient colour if gradient is enabled. With gradient disabled, it uses the foreground colour.

Thanks again

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

4 participants