return true;
//Set values to map
gInsMax.push_back(0.899);
the return
statement there means that the function returns and what's below that won't get executed. So your values are never pushed into the vector.
Now, if you move the return true;
statement to the end of the function, the values will be pushed back. Your gInMax
vector has an initial size of kNumOsc
, as per its definition:
std::vector<float> gInsMax(kNumOscs);
The initial elements will be initialised to 0. Calling push_back()
on a vector
will append values to it, so once you are done pushing back values, gInMax
will contain 16 elements:
{0, 0, 0, 0, 0, 0, 0, 0, 0.899, 0.895, 0.874, 0.899, 0.925, 0.929, 0.919, 0.933}
which is not what you want, because this line:
gIns[c] = map(gIns[c], 0.f, gInsMax[c], 0.f, 1.f);
will only use the first 8 elements which are all 0.
So instead of calling push_back()
, you should just set the existing values:
//Set values to map
gInsMax[0] = 0.899;
gInsMax[1] = 0.895;
gInsMax[2] = 0.874;
gInsMax[3] = 0.899;
gInsMax[4] = 0.925;
gInsMax[5] = 0.929;
gInsMax[6] = 0.919;
gInsMax[7] = 0.933;
A more concise way of doing this is to change the definition to:
std::vector<float> gInsMax = { 0.899, 0.895, 0.874, 0.899, 0.925, 0.929, 0.919, 0.933 };
You can also be more concise in your scope.log()
call.
scope.log(gIns[0], gIns[1], gIns[2], gIns[3], gIns[4], gIns[5], gIns[6], gIns[7]);
There is an overloaded log()
method that takes a pointer to a C array of floats instead of enumerating all values:
void Scope::log ( const float * values )
Logs a frame of data to the scope.
Accepts a pointer to an array of floats representing each channel's value in ascending order.
Parameters
values a pointer to an array containing numChannels values.
So you can get the pointer to the first element of the vector with gIn.data()
and pass that to scope.log()
:
scope.log(gIn.data());
In short, here's a working and less verbose example. Other improvements I included:
- removed
gInverseSampleRate
as it's unused
- replace the constant
8
with kNumOscs
, which should save you headaches in the future when you change that.
- check the number of channels is consistent
#include <Bela.h>
#include <cmath>
#include <libraries/Scope/Scope.h>
#include <iostream>
#include <libraries/Oscillator/Oscillator.h>
#include <vector>
Scope scope;
int gAudioFramesPerAnalogFrame = 0;
const size_t kNumOscs = 8;
std::vector<Oscillator> gOscs;
std::vector<float> gIns(kNumOscs);
std::vector<float> gInsMax = { 0.899, 0.895, 0.874, 0.899, 0.925, 0.929, 0.919, 0.933 };
bool setup(BelaContext *context, void *userData)
{
if(gIns.size() != gInsMax.size() || gIns.size() != context->analogInChannels)
{
fprintf(stderr, "Wrong number of analog ins\n");
return false;
}
for(unsigned int n = 0; n < kNumOscs; ++n)
gOscs.push_back({context->audioSampleRate});
// setup the scope with kNumOscs channels at the audio sample rate
scope.setup(kNumOscs, context->audioSampleRate);
if(context->analogFrames)
gAudioFramesPerAnalogFrame = context->audioFrames / context->analogFrames;
return true;
}
void render(BelaContext *context, void *userData)
{
for(unsigned int n = 0; n < context->audioFrames; n++)
{
for(unsigned int c = 0; c < gOscs.size() && c < context->analogInChannels; ++c)
{
// Read values from inputs and map them to their maximum values.
gIns[c] = analogRead(context, n / gAudioFramesPerAnalogFrame, c);
gIns[c] = map(gIns[c], 0.f, gInsMax[c], 0.f, 1.f);
}
// log mapped values into scope.
scope.log(gIns.data());
}
}
void cleanup(BelaContext *context, void *userData)
{
}