Dumb question: Where is the documentation for JUCE's maths/tools functions/classes? [SOLVED]

#1

Things like jmap, jmin, jmax etc.

I want to add some kind of linear interpolation and I’m sure JUCE already includes it. Just don’t know where to find it.

Bonus question: Why does JUCE come with its own String class?

#2

Here it is: https://docs.juce.com/develop/group__juce__core-maths.html

For linear interpolation I usually use jmap:

// interpolate between p0 (x0, y0) and p1 (x1, y1)
auto interpolated = jmap (x, x0, x1, y0, y1);

The String class is there for historic reasons, when the std::string was not so common yet and the author added a bunch of useful stuff. Today it is up to the user, which one to prefer… But it makes the code nice consistent. Some classes were remodelled to use the std ones internally (e.g. ScopedPointer), who knows, if that happens to the string class as well, but TBH I doubt that.

#3

Woah, back in the dark ages, eh?

With the linear interpolation, perhaps I don’t mean that? :thinking: What I want to do is every time a variable is changed (i.e. frequency) I want it to glide from the previous value to the new value in X amount of time (or steps).

Btw, appreciate the attention even on a fine Sunday afternoon!

#4

Ah, I see. That’s what SmoothedValue is for…

1 Like
#5

It’s a thing that just commonly happens with C++ frameworks. The framework developers want to have complete control over such a commonly used data type. Also, std::string is still missing all kinds of convenience functionalities, like turning the string upper/lowercase.

Don’t use std::string in Juce based code. (Unless required by some external thing.) You would just be converting back and forth between std::strings and Juce Strings.

1 Like
#6

I don’t believe that’s true.

From the ScopedPointer documentation:

This class is deprecated. 
You should use std::unique_ptr instead.
#7

Seems you are right, sorry for repeating false information. I blame my source :wink:

1 Like
#8

Honestly, I wish ScopedPointer was remodeled to use std::unique_ptr internally. Its syntax is much cleaner.

1 Like
#9

Hi Daniel,

Can you explain how to use SmoothedValue please? :relieved: It’s a class, so I’m assuming I’ll need to instantiate an object first, let’s call it smoothValue.

Let’s say I’m generating a sine wave like this:

std::sin (2.0f * pi * freq * static_cast<float>(pos++) / sampleRate);

then where freq is called (for every sample in the buffer) I would do this?:

std::sin (2.0f * pi * smoothValue.getnextValue() * static_cast<float>(pos++) / sampleRate);

Then every time I want to change the frequency I have to set it with smoothValue.setTargetValue()?

And what if, for example, I were using the the ToneGeneratorAudioSource class… Maybe like this:

void audioDeviceIOCallback (const float** inputChannelData, int numInputChannels,
                                    float** outputChannelData, int numOutputChannels,
                                    int numSamples) override
    {
        AudioBuffer<float> buffer(outputChannelData, numOutputChannels, numSamples);
        toneGenSource.getNextAudioBlock(AudioSourceChannelInfo(buffer));
    }

I shouldn’t modify the internals, so instead, would I just throw a toneGenSource.setFrequency(smoothValue.getNextValue()); into audioDeviceIOCallback(...) so it gets updated repeatedly?

Thanks! :slight_smile:

#10

In principle, yes, but the smoothing would happen at only each audio processing callback which might not be enough to smooth the changes enough. But if you want to try it anyway, just remember that the sample rate you need to give to the smoother isn’t going to be sample rate of the audio device. You rather need to figure out how often the audio IO callback is called and use that as the “sample rate”.

To get properly dezippered frequency (or gain) changes in an oscillator, the smoothing needs to be built into the oscillator itself. I don’t think the Juce ToneGeneratorSource is really meant to be used for anything else but simple tests. The Juce dsp::Oscillator class is better suited since it has internal smoothing for the frequency changes.

#11

Thanks Xenakios, btw, there’s at least one beer waiting for you if I ever meet you at a future meetup!

Do I need to #include anything? In the projucer, my project has the juce_audio_basics module.

The error I’m getting is: error: ‘SmoothedValue’ does not name a type

Here’s my code:

class AudioApp : public AudioIODeviceCallback
{
private:
    SmoothedValue<double, ValueSmoothingTypes::Multiplicative> freqGlider;
    ToneGeneratorAudioSource toneGenSource;
    AudioDeviceManager dm;

public:
    AudioApp()
    {
        dm.addAudioCallback(this);
        dm.initialiseWithDefaultDevices(0,1);
        freqGlider.setTargetValue(0); // something about Multiplicative type can't actually reach 0
        
    }
    
    void audioDeviceIOCallback (const float** inputChannelData, int numInputChannels,
                                    float** outputChannelData, int numOutputChannels,
                                    int numSamples) override
    {
        toneGenSource.setFrequency(freqGlider.getNextValue()); // update the glider frequency
        AudioBuffer<float> buffer(outputChannelData, numOutputChannels, numSamples);
        toneGenSource.getNextAudioBlock(AudioSourceChannelInfo(buffer));
    }
    
    void audioDeviceAboutToStart(AudioIODevice* device) override
    {
        toneGenSource.prepareToPlay(device->getCurrentBufferSizeSamples(), device->getCurrentSampleRate());
    }
    
    void audioDeviceStopped() override
    {
        toneGenSource.releaseResources();
    }

    void setFreq(double value)
    {
        freqGlider.setTargetValue(value);
    }
};
#12

Hmm, SmoothedValue<double, ValueSmoothingTypes::Multiplicative> freqGlider; as a class member compiles OK for me. What Juce version are you on?

#13

Well, you caught me out. :slight_smile: I was behind by one version, Anyway, I updated (which I assume on GNU/Linux is as simple as just trashing the old ~/JUCE folder and unzipping the new JUCE download in its place.

I created a new console app. It compiled and ran with success, but then copying the code into it gets me the same error.

Don’t worry about it though. It’s not really that big a deal. I’m busy consuming the contents of that video you linked me, which btw is perfect, and more important and I’m soon going to be fresh installing my Linux Distro anyway, (because I’ve got other JUCE problems that I have to use workarounds for)