HISE Logo Forum
    • Categories
    • Register
    • Login

    HISE Filter Display Inconsistencies

    Scheduled Pinned Locked Moved General Questions
    31 Posts 9 Posters 2.0k Views
    Loading More Posts
    • Oldest to Newest
    • Newest to Oldest
    • Most Votes
    Reply
    • Reply as topic
    Log in to reply
    This topic has been deleted. Only users with topic management privileges can see it.
    • A
      aaronventure
      last edited by

      I've been running HISE in PluginDoctor for a few days while working in ScriptNode and this afternoon I noticed a rather large discrepancy between the actual impulse response and the displayed curve in HISE.

      Here's a couple:

      1 pole
      1polegif.gif

      SVF
      svflp.gif

      Allpass (wut)
      allpass.gif

      Ladder 4pole LP
      ladder 4pole lp.gif

      In trying to get my bearings by finding out which settings correspond to the ones on the FabFilter Pro-Q (as I basically grew up with that thing, using it every day for nearly 15 years), I found that the only way to match its default low-pass/high-pass 12dB/oct at q 1.0 is to use the Biquad LP Rez and set the q to 0.7071 (square root of 2 divided by 2).

      Same for the peak filters, FabFilter Q1.0 = HISE Q=0.7071, though HISE is noticeably crampy and needs oversampling at high frequencies (which FabFilter might already be doing).

      C griffinboyG ustkU 3 Replies Last reply Reply Quote 2
      • C
        Consint @aaronventure
        last edited by

        I also wanted to draw attention to this problem, except that I don't have such good proof, only my auditory impression. The resonance of the SVF LP, despite a Q of 0, is clearly audible. And just like the ladder filter, the Moog filter also makes the signal significantly louder overall.

        I also noticed that the SVF BP and Notch Filter display in Scriptnode is broken.

        (Is the forum actually the right place for bug reports?)

        d.healeyD 1 Reply Last reply Reply Quote 2
        • d.healeyD
          d.healey @Consint
          last edited by

          @Consint said in HISE Filter Display Inconsistencies:

          (Is the forum actually the right place for bug reports?)

          Yes, but it's good to put them on github too and link back to the thread.

          Libre Wave - Freedom respecting instruments and effects
          My Patreon - HISE tutorials
          YouTube Channel - Public HISE tutorials

          1 Reply Last reply Reply Quote 1
          • A
            aaronventure
            last edited by

            FAUST fi.svf for comparison

            svf faust.gif

            ustkU 1 Reply Last reply Reply Quote 1
            • ustkU
              ustk @aaronventure
              last edited by ustk

              @aaronventure To me it is a matter of convention, and the "zeroing" position of a quality factor should normally be 0.707. This is because the measured bandwidth is made at 3dB, corresponding to the half power. The power is proportional to the voltage squared, you get sqrt(2)/2=0.707
              If some brands are using, a Q of 1, I think it's just because it looks better and less confusing for the end user. Another explanation could be that the point of vue has been taken from the voltage instead of the power, dropping that sqrt, so 2/2=1…
              Power POV? Voltage POV? User friendly normalisation? Like there are not enough choices… 😁

              Can't help pressing F5 in the forum...

              1 Reply Last reply Reply Quote 1
              • griffinboyG
                griffinboy @aaronventure
                last edited by griffinboy

                @aaronventure
                Thank you, this is very interesting, and timely, as I was just starting to work on this myself.
                I've been using the curve 'parametric eq' built into HISE.
                I wonder how that stacks up...
                I too have noticed the behaviour being very different to ProQ3

                It would be great to be able to oversample the built in CURVE_EQ!
                Cramping is something that I am concerned about.

                1 Reply Last reply Reply Quote 0
                • A
                  aaronventure
                  last edited by aaronventure

                  Alright something definitely feels fishy here.

                  The parametric EQ low pass at q=1 behaves exactly like the Pro-Q3 lowpass at 12dB/oct.It's a biquad filter.

                  I now built HISE with HISE_USE_SVF_FOR_CURVE_EQ=1 and the default lowpass at q=1 now looks like the one from Faust I posted a gif of above.

                  parametric svf.gif

                  The svf_eq node in Scriptnode also looks correct

                  69a045d8-e9d7-4fe2-88ea-a712f00b52f3-image.png

                  But the standard svf node is fucked just like the Filter module

                  173ced41-d0cc-4e30-81bd-7d501e9a30b5-image.png

                  SVF node allpass looks correct at first

                  f15ddf24-69c0-4a1c-a5a5-2d5faaa226c6-image.png

                  But will straight up attempt to murder you as you move it up
                  https://github.com/christophhart/HISE/issues/527

                  You can see the filter stop working after I drive the frequency high enough. The math seems to be wrong and it falls off the edge of the cliff, taking everything with it as it zooms past 20k while the Frequency parameter is nowhere near.
                  svf allpass .gif

                  Conclusions:

                  • SVF in the Filters module and the SVF node are busted
                  • stay away from the default Allpass like the plague. If you need Allpass right now, get Faust, RNBO or write it yourself in SNEX/C++
                  • use the SVF_EQ node
                  • build HISE with HISE_USE_SVF_FOR_CURVE_EQ=1 and enjoy the SVF EQ, just keep in mind that the LP and HP will be more resonant by default, so use Q=0.7071

                  Bonus for the end: biquad node HP thinks it's an SVF
                  biquad hp.gif

                  griffinboyG DanHD 2 Replies Last reply Reply Quote 4
                  • griffinboyG
                    griffinboy @aaronventure
                    last edited by

                    @aaronventure
                    Thank you!
                    This is much appreciated, especially the
                    'HISE_USE_SVF_FOR_CURVE_EQ=1'
                    trick.

                    I did not know that there were modifiers that can be applied to the built in parametric eq, that is great to know.

                    A 1 Reply Last reply Reply Quote 0
                    • A
                      aaronventure @griffinboy
                      last edited by

                      @griffinboy

                      A bit more:

                      Default Parametric EQ harmonic analysis vs Pro-Q3

                      30cd9950-9473-47ef-9330-d6c57cb054b4-image.png

                      SVF Parametric EQ harmonic analysis vs Pro-Q3

                      9fa699b7-67ca-4ea4-aa4c-ccab3a13f6d4-image.png

                      Yes, definitely use the SVF parametric EQ. Especially if you're gonna be doing anything with distortion. Frankly it should be default, with the lack of zipper noises and a clean response, it's an upgrade for everyone using the Parametric EQ.

                      griffinboyG 1 Reply Last reply Reply Quote 1
                      • griffinboyG
                        griffinboy @aaronventure
                        last edited by

                        @aaronventure
                        Oh! Fantastic.
                        Thank you for sharing this knowledge, you have saved me :beaming_face_with_smiling_eyes:

                        1 Reply Last reply Reply Quote 0
                        • DanHD
                          DanH @aaronventure
                          last edited by

                          @aaronventure said in HISE Filter Display Inconsistencies:

                          • stay away from the default Allpass like the plague. If you need Allpass right now, get Faust, RNBO or write it yourself in SNEX/C++

                          There's a dedicated Allpass filter node in scriptnode that works fine.
                          Screenshot 2024-06-07 at 09.36.48.png

                          In general the filters are, however, all over the place, with lots of options that don't actually exist, don't display properly, or are broken, as you have discovered. I've had to do several workarounds to display things properly on my UIs.

                          Ultimately it seems Hise uses the same display for all the filters. The ladder filter is the only exception and uses double values for the same display, which again doesn't accurately display what the filter is doing, but allows for a steeper slope and higher Q values.

                          I did recently discover that in scriptnode you can set multiple filters to the same external filter slot for your UI filter display tile, and that the filters will be summed graphically, so you can display steeper slopes if you cascade filters. This would also allow you to amend the Q values to more accurately display filter behaviour.

                          DHPlugins / DC Breaks | Artist / Producer / DJ / Developer
                          https://dhplugins.com/ | https://dcbreaks.com/
                          London, UK

                          Christoph HartC A 2 Replies Last reply Reply Quote 2
                          • Christoph HartC
                            Christoph Hart @DanH
                            last edited by

                            Ultimately it seems Hise uses the same display for all the filters.

                            Yes that's true - it creates more or less the same curve because internally the display uses the IIRC coefficients from the biquad filters. In 99% of the cases it's enough as the display on the UI should just tell you "yeah, I'm taking away the high frequencies of the saw wave". Now with HISE venturing more and more into audio effects there might be an increased demand for precise displaying of the filter graph: I always thought the filter curve to be a rough approximation of what's going on and there is quite some work to be done if the aim is to be 100% mathematically precise.

                            HISE_USE_SVF_FOR_CURVE_EQ=1 should be default

                            Yeah, I thought about that too - I started using this setting for almost every commercial project I did so far but I didn't want to change the default for backwards compatibility - it's a rather drastic change of sound and silently changing this for old projects is not an option. There is a way of "soft-migration", but it's rather complex:

                            • add HISE_USE_SVF_FOR_CURVE_EQ=1 to the extra definitions whenever you create a new project
                            • use HISE_USE_SVF_FOR_CURVE_EQ=1 in HISE as default
                            • use HISE_USE_SVF_FOR_CURVE_EQ=0 in compiled plugins as default

                            stay away from the default Allpass like the plague.

                            Gonna solve that one now...

                            ustkU 1 Reply Last reply Reply Quote 1
                            • ustkU
                              ustk @Christoph Hart
                              last edited by

                              @Christoph-Hart I think having a mathematically correct representation is a must. Many users are sound engineers looking for precise tools, not just a rough approximation of what it's doing behind.
                              What I wonder for a long time is how to get the curve out of a homemade SNEX filter

                              Can't help pressing F5 in the forum...

                              Christoph HartC 1 Reply Last reply Reply Quote 0
                              • Christoph HartC
                                Christoph Hart @ustk
                                last edited by

                                @ustk The whole topic of filter design is not really my strong suit, but the problem is that the visualization of a filter graph cannot be generalized and the current FilterDisplay expects a second order biquad IIRC algorithm and turns the five coefficients into a frequency / magnitude plot using some advanced math calculations that I don't understand. Hence my "ignorance" about subtle differences: either you live with those (slight) inconsistencies or you have to implement a custom visualization for each filter which will completely break the API.

                                I might be able to improve the "dummy" IIRC coefficient generation to match the filters better, but we're not achieving 100% mathematical accuracy for all filters with this.

                                Things like plugin doctor can just create a sine sweep and sample the response but that is not an option for the display that needs to update this with 60fps on real input.

                                I'm open to suggestions though as I know that you're a bit more in the topic. Adding the option for SNEX filter displays would currently require for you to calculate the IIRC coefficients yourself and pass them into a callback TBD.

                                ustkU 1 Reply Last reply Reply Quote 0
                                • A
                                  aaronventure @DanH
                                  last edited by aaronventure

                                  @DanH said in HISE Filter Display Inconsistencies:

                                  There's a dedicated Allpass filter node in scriptnode that works fine.

                                  SVF allpass is fixed now but this one is still messed up. It's just like the filter version in my original post

                                  It's not quite passing all the frequencies.
                                  7ed9aa63-718a-46eb-b36a-9d82a563ada7-image.png

                                  @DanH said in HISE Filter Display Inconsistencies:

                                  I did recently discover that in scriptnode you can set multiple filters to the same external filter slot for your UI filter display tile, and that the filters will be summed graphically, so you can display steeper slopes if you cascade filters. This would also allow you to amend the Q values to more accurately display filter behaviour.

                                  Valuable info, thank you. Documentation worthy for sure.

                                  @Christoph-Hart said in HISE Filter Display Inconsistencies:

                                  it's a rather drastic change of sound

                                  How so? Here's a screenshot of a few filters 100Hz/3dB, 1000Hz/8dB, 5Khz LP.

                                  On Pro-Q3, all Q values are at 1.0 for both the peaks and the LP.

                                  First we see the default parametric eq with biquad filters. Peaks need Q=0.7071 to match up with the Pro-Q3 peaks at Q=1.0
                                  b4d01edd-3530-4463-b29a-20e631342eec-image.png

                                  Now here's the SVF parametric EQ. We can see it all match up nicely. Peaks still need Q=0.7071, but I also had to set the LP to Q=0.7071.
                                  79d3bc4f-d2b0-4eea-b6bf-9a4f4e4e5cc7-image.png

                                  So they look pretty much the same. All you have to do, once you build the EQ with SVF, is make sure your low cut and high cut is set to 0.7071.

                                  And here's your proof. I rendered an audio file with a random crazy EQ setting.

                                  a92d0fb9-4d18-4f2d-b061-ef6f02bc1504-image.png

                                  Bounced it, saved the project, rebuilt HISE with SVF, made sure the LP Q was 0.7071. Bounced that, inverted phase. There's definitely differences, but they're at -80dB. And I will bet you that's the harmonic distortion which comes with the biquads, which you can see in my post above. And the harmonic distortion increases with the number of filters, so in a scenario where you're using fewer than 10 and exporting 16bit, there's (figuratively) no difference at all.

                                  b547afac-1cae-4030-b4aa-1b46c061d4f0-image.png

                                  I wouldn't call that a rather drastic change of sound.

                                  Christoph HartC 1 Reply Last reply Reply Quote 1
                                  • Christoph HartC
                                    Christoph Hart @aaronventure
                                    last edited by

                                    @aaronventure nice detective work! It's still a delicate change because just telling people to change the Q of every filter they used so far is not a nice thing to do, but with your recent findings, the migration path might be even easier:

                                    OK, so just to be sure:

                                    svf_Q / sqrt(2) == eq_Q
                                    

                                    so all it takes it the Q of the SVF_EQ to be multiplied with sqrt(2) to make the response identical? If that's the case, then the change can be made even easier:

                                    • enable HISE_USE_SVF_FOR_CURVE_EQ=1 by default for all build configurations or remove that codepath entirely as there is no real advantage of using the ol' filters.
                                    • add another preprocessor, HISE_COMPENSATE_SVF_Q_FACTOR which will be set to 1 in HISE and new projects and 0 for old compiled plugins. If that's active then it will just apply that factor before setting the Q. Do we want this to affect the parametric bands only or also the filter nodes in scriptnode?

                                    As long as you have your sherlock Holmes magnifying glasses out, can you check if that Q factor is linear? So if you set the Q to 6.0 in the non SVF filter, it should sound the same as the SVF filter with a Q of 4.242?

                                    A 1 Reply Last reply Reply Quote 2
                                    • A
                                      aaronventure @Christoph Hart
                                      last edited by

                                      @Christoph-Hart

                                      It's even simpler than you think.

                                      For the peak filters, the Q values are the same for the biquad and SVF version of the PEQ. the biquad PEQ LP/HP Q does nothing, there's no resonance control. But in order to match how the LP/HP biquad filters look in the PEQ, once you build the SVF PEQ, you need to set the LP and HP Q to 0.7071 or sqrt(2)/2, as the resonance control is now unlocked, i.e. SVF LP/HP have resonance control.

                                      You can verify this right now in scriptnode using the svf_eq (NOT the svf ) node vs the biquad node, regardless of how you build the PEQ.

                                      svf biquad.gif

                                      I'm unsure whether your preproc will be worth much, because the PEQ Q control was still available for the low pass and high pass filters, even though it did nothing. So if they tweaked it at all, once they build the new commit with default SVF EQ, even if they build with that preproccesor flag that compensates, they'll still hear the difference.

                                      But if that compensation affects the SVF LP/HP in general, it'll fuck with the one in scriptnode, too.

                                      I think you're overthinking it, it's just for the Parametric EQ. The svf_eq node is fine (the svf node is fucked just like the Filter module). Your commit tag or however you choose to communicate this should say something like "Parametric EQ is now SVF by default. Enjoy zipperless automation and distortion free equalisation with Q-unlocked LP/HP. If you want to maintain the previous response of LP/HP in your parametric EQ, set the Q to 0.7071 (previously it did nothing).

                                      Here's another one which confirms that the Q for biquad peaks is the same as the Q for SVF peaks. Again, you can go do this in scriptnode right now and do a null test. Shelves are the same. Same phase response, too.

                                      cf613f6b-e46b-4126-a5dc-3ef63f39cb8d-image.png

                                      1 Reply Last reply Reply Quote 2
                                      • ustkU
                                        ustk @Christoph Hart
                                        last edited by ustk

                                        @Christoph-Hart said in HISE Filter Display Inconsistencies:

                                        the problem is that the visualization of a filter graph cannot be generalized

                                        Yeah I was expecting this answer unfortunately...

                                        Things like plugin doctor can just create a sine sweep and sample the response but that is not an option for the display that needs to update this with 60fps on real input.

                                        Sure it's not a comparison that can be made. a tool that analyses a signal spends most of the cycles doing so, while it's not a job for an audio plugin which needs to just show the (approximated) transfer curve

                                        I'm open to suggestions though as I know that you're a bit more in the topic. Adding the option for SNEX filter displays would currently require for you to calculate the IIRC coefficients yourself and pass them into a callback TBD.

                                        That would be a great thing indeed! But I wouldn't say I'm more in the topic, even if definitely interested, I lack advanced mathematics since I much preferred playing guitar than going to the math class! Anyway I'm on that track so having a way to use the computed coeffs out of a SNEX node would be amazing

                                        Can't help pressing F5 in the forum...

                                        Christoph HartC 1 Reply Last reply Reply Quote 1
                                        • Christoph HartC
                                          Christoph Hart @ustk
                                          last edited by

                                          @ustk I'm currently toying around with a new way of handling this - basically it keeps the old behaviour of approximating the graph with IIR coefficients for all the two pole filter types, but you can override it with a custom function that can calculate any filter response.

                                          // Return the magnitude (or phase) value for the given frequency
                                          double getPlotValue(bool getMagnitude, double normedXAxis)
                                          {
                                              return someValue;
                                          }
                                          

                                          If the filter type overrides that function it will prefer this for calculating the plot. Now with my limited filter knowledge I figured out how to write the transfer function for the one pole filter and the result is promising:

                                          81a0fc33-c9ac-4d0f-91cb-3ebe8b3acbec-image.png

                                          but to figure out the transfer function for the other filter types (ladder, moog, etc) would require me to actually understand this paper lol...

                                          A LindonL Dan KorneffD 3 Replies Last reply Reply Quote 1
                                          • A
                                            aaronventure @Christoph Hart
                                            last edited by

                                            @Christoph-Hart what does chatgpt say?

                                            Christoph HartC 1 Reply Last reply Reply Quote 0
                                            • First post
                                              Last post

                                            47

                                            Online

                                            1.7k

                                            Users

                                            11.7k

                                            Topics

                                            101.9k

                                            Posts