Potentiometers changing values of other/multiple pins!!

Hello everyone, first time poster here (and new to Arduino, go easy on me)! Sorry if my explanation is poor.

I'm working on a project that involves using multiple pots to control parameters in a Pure Data synth patch (using a MIDI out from the Arduino). It is all well and good, apart from two things;

when twisting two of the potentiometers, they change the parameter they are supposed to...but also change another parameter at the same time, which has its own potentiometer and analogPin. In other words, when I twist a pot to change the volume or the resonance, it also changes the pitch!

Does anyone have any suggestions as to what this could be? I'm quite confused as the other six potentiometers work fine. The board I'm using is an Arduino Mega 2560, I'll attach my code if anyone is curious.

Please do reply if you can help, this is semi-urgent I'm afraid :frowning:

Thanks!

Assignment.ino (3.94 KB)

I should have mentioned: the pitch pot (that the volume/resonance pots are controlling when they aren't meant to be) is actually a soft ribbon pot. When there is pressure on the ribbon, the volume/resonance pots no longer affect the pitch, it is only when the ribbon pot isn't being pressed

Hello and welcome :slight_smile:

Maybe this could help: analogRead Noise - Project Guidance - Arduino Forum

Hi,
I know it sounds stupid, but read each analog input twice, and use the second value.

The reason is that there is only one ADC and it has to be switched from A0 to A1 to A2 etc.
If its done to quickly, the ADC does not have time to do a full read of the next input and you have the analog level of the previous input still on the ADC input.
The soft ribbon pot when not touched will also leave the analog input open circuit, floating, not good as it picks up noise and interference.

Tom.... :slight_smile:

TomGeorge:
Hi,
I know it sounds stupid, but read each analog input twice, and use the second value.

The reason is that there is only one ADC and it has to be switched from A0 to A1 to A2 etc.
If its done to quickly, the ADC does not have time to do a full read of the next input and you have the analog level of the previous input still on the ADC input.
The soft ribbon pot when not touched will also leave the analog input open circuit, floating, not good as it picks up noise and interference.

Tom.... :slight_smile:

By this, do you mean;

VolValue = analogRead(VolPin); // Reads the value from the VolPin
VolValue2 = analogRead(VolPin); // Reads second value from VolPin
scaled_VolValue = map(VolValue2, 0, 1023, 0, 127); // map voltage of second reading to MIDI values

Would I create another int for the second value I read (in this case VolValue2)?

Thank you both for responding, I really appreciate it!

Hi,

VolValue = analogRead(VolPin); // Reads the value from the VolPin
VolValue = analogRead(VolPin); // Reads value from VolPin for the second time

will be enough, just over write the first read value, no need for new int.

Tom..... :slight_smile:

Thanks a lot, I'll try it when I get a chance later today and post if that fixes it :slight_smile:

TomGeorge:
The soft ribbon pot when not touched will also leave the analog input open circuit, floating, not good as it picks up noise and interference.

Can anything be down with the soft pot? I've tried using a pull down resistor, which I think makes the value go to 0 when it is not being pressed, but as I've scaled the pot's voltage to MIDI values, when it goes to zero it is still playing a very low pitch

I've tried using a pull down resistor, which I think makes the value go to 0 when it is not being pressed

Yes that is the correct thing to do.

but as I've scaled the pot's voltage to MIDI values, when it goes to zero it is still playing a very low pitch

You need to skip the scaling when you read the input as zero and not use that value to play anything. In other words only play something when you have a non zero value.

Update: It appears reading the pin twice doesn't change it: when nothing is pressing the softpot, the volume and resonance pins still change the pitch :frowning: argh!

Grumpy_Mike:
Yes that is the correct thing to do.
You need to skip the scaling when you read the input as zero and not use that value to play anything. In other words only play something when you have a non zero value.

That sounds promising, but I'm not very sure how to do that in the code (once again, sorry about my complete lack of knowledge, I'm very new to this!

andrwsmth:
Update: It appears reading the pin twice doesn't change it: when nothing is pressing the softpot, the volume and resonance pins still change the pitch :frowning: argh!

Is that with pull down resistors fitted on ALL pots?

but I'm not very sure how to do that in the code

Post your failed attempt, using code tags and we can help you.

Grumpy_Mike:
Is that with pull down resistors fitted on ALL pots?
Post your failed attempt, using code tags and we can help you.

No no, just on the soft pot. I'm happy to show my code, but what are code tags, just comments?

but what are code tags,

Have you read the "How to use this forum" sticky post?

Code tags are given by the icon on the top of the reply box to the left of the quote icon. Paste your code between what comes up when you click it.

Ah okay, there you go. I've taken out the second analogReads for the pots as that was not working. Like I say, I have a 10k resistor between the soft pot and ground to pull down, but I'm still having this problem of a very low pitched note when the soft pot isn't pressed, as well as the VolPin and ResPin changing the pitch (as well as the things they're meant to change) when the soft pot isn't pressed

/**RIBBON SYNTH ARDUINO CODE**/

/*Analogue pins*/
const int VolPin = A13;  // Master volume Pin set to A13 (moved from A0 to A13)
const int RibbonPin = A1; // Ribbon pot pin set to A1
const int SweepSpeed = A2; // Sweet speed pot pin set to A2
const int SweepDepth = A3; // Sweep depth pot int set to A3;
const int CenterFreqPin = A4;   //Filter frequency Pin set to A4
const int ResPin = A5;   //Resonance pin on A5
const int RevDryWet = A8; // Reverb Dry Wet set to A8;
const int RevRoomsize = A9; // Reverb room size set to A9;
const int RevDamping = A10; // Reverb damping set to A10;

/*Digital pins*/
const int switchPin = 12; // On/off toggle set to Digital 12
const int led = 10; // On LED set to Digital 8

/*Variable declarations*/
int VolValue = 0;
int RibbonValue = 0;
int SSpeedValue = 0;
int SDepthValue = 0;
int CenterFreqValue = 0;
int ResValue = 0;
int DryWetValue = 0;
int RoomsizeValue = 0;
int DampingValue = 0;

/*Scaled values to be used in map functions*/
int scaled_VolValue;
int scaled_RibbonValue;
int scaled_SSpeedValue;
int scaled_SDepthValue;
int scaled_CenterFreqValue;
int scaled_ResValue;
int scaled_DryWetValue;
int scaled_RoomsizeValue;
int scaled_DampingValue;

int switchState;

/*Setup Function*/
void setup() 
{
 Serial.begin(31250);
 pinMode(led, OUTPUT);
 pinMode(switchPin, INPUT);
 
 pinMode(VolPin, INPUT);
 pinMode(RibbonPin, INPUT);
 pinMode(SweepSpeed, INPUT);
 pinMode(SweepDepth, INPUT);
 pinMode(CenterFreqPin, INPUT);
 pinMode(ResPin, INPUT);
 pinMode(RevDryWet,INPUT);
 pinMode(RevRoomsize, INPUT);
 pinMode(RevDamping, INPUT);
 }

/*Main Loop*/
void loop() {
   
VolValue = analogRead(VolPin);    // Reads second value from the VolPin
scaled_VolValue = map(VolValue, 0, 1023, 0, 127); // Scales voltage levels to midi values

RibbonValue = analogRead(RibbonPin);    // Reads second value from the Ribbon Pin
scaled_RibbonValue = map(RibbonValue, 0, 1023, 0, 127); // Scales voltage levels to midi values

SSpeedValue = analogRead(SweepSpeed);    // Reads the value from the Sweep Speed Pin
scaled_SSpeedValue = map(SSpeedValue, 0, 1023, 0, 127); // Scales voltage levels to midi values

SDepthValue = analogRead(SweepDepth);    // Reads the value from the Sweep Depth Pin
scaled_SDepthValue = map(SDepthValue, 0, 1023, 0, 127); // Scales voltage levels to midi values

CenterFreqValue = analogRead(CenterFreqPin);    // Reads the value from the CenterFreqPin
scaled_CenterFreqValue = map(CenterFreqValue, 0, 1023, 0, 127); // Scales voltage levels to midi values
  
ResValue = analogRead(ResPin);    // Reads the value from the Res Pin
scaled_ResValue = map(ResValue, 0, 1023, 0, 127); // Scales voltage levels to midi values

DryWetValue = analogRead(RevDryWet);  //Reads the value from the DryWet pin
scaled_DryWetValue = map(DryWetValue, 0, 1023, 0, 127);  //Scales voltage levels to midi values

RoomsizeValue = analogRead(RevRoomsize);  //Reads the value from the Roomsize pin
scaled_RoomsizeValue = map(RoomsizeValue, 0, 1023, 0, 127);  //Scales voltage levels to midi values

DampingValue = analogRead(RevDamping);  //Reads the value from the Damping pin
scaled_DampingValue = map(DampingValue, 0, 1023, 0, 127);  //Scales voltage levels to midi values

switchState = digitalRead(switchPin);  //Reads the state of the toggle switch pin
  
//if the switch is high, turn on LED and send 'ON' data to the line object in PD 
if (switchState == HIGH)
{
  digitalWrite(led, HIGH);   
  Serial.write(0xB0);
  Serial.write(13);
  Serial.write(1);
}
//else, LED is turned off and send 'OFF' data to the line object in PD
else 
{
  digitalWrite(led, LOW); 
  Serial.write(0xB0);
  Serial.write(14);
  Serial.write(0);
}

//Code to send scaled MIDI values from potentiometers to control sliders in PD

//Volume MIDI
Serial.write(0xB0);
Serial.write(1);
Serial.write(scaled_VolValue);

//Ribbon MIDI
Serial.write(0xB0);
Serial.write(2);
Serial.write(scaled_RibbonValue);

//Sweep Speed MIDI
Serial.write(0xB0);
Serial.write(3);
Serial.write(scaled_SSpeedValue);

//Sweep Depth MIDI
Serial.write(0xB0);
Serial.write(4);
Serial.write(scaled_SDepthValue);

//Centre Freqency MIDI
Serial.write(0xB0);
Serial.write(5);
Serial.write(scaled_CenterFreqValue);

//Resonance MIDI
Serial.write(0xB0);
Serial.write(6);
Serial.write(scaled_ResValue);

//Reverb DryWet MIDI
Serial.write(0xB0);
Serial.write(9);
Serial.write(scaled_DryWetValue);

//Reverb Roomsize MIDI
Serial.write(0xB0);
Serial.write(10);
Serial.write(scaled_RoomsizeValue);

//Reverb Damping Value
Serial.write(0xB0);
Serial.write(11);
Serial.write(scaled_DampingValue);

delay(1); //Small delay for more accurate potentiometer readings
}

That code is very turgid and badly organized, however you need to skip over something if if returns zero.

So replace:-

//Ribbon MIDI
Serial.write(0xB0);
Serial.write(2);
Serial.write(scaled_RibbonValue);

with:-

//Ribbon MIDI
if (RibbonValue == 0){
   Serial.write(0xB0);
   Serial.write(2);
   Serial.write(scaled_RibbonValue);
}

I've taken out the second analogReads for the pots as that was not working.

So put then back and place a small delay between them

RibbonValue = analogRead(RibbonPin);
delay(1);
RibbonValue = analogRead(RibbonPin);

If that doesn't help then your situation is not what you described and we need to see a schematic (not a Fritzing abortion) and a clear photograph not more than 1000 wide.

Grumpy_Mike:
That code is very turgid and badly organized.

Okay, any hints on how I can make it better organised?

//Ribbon MIDI
if (RibbonValue == 0){
Serial.write(0xB0);
Serial.write(2);
Serial.write(scaled_RibbonValue);
}

Okay, so this means that it will only produce a pitch when the reading is 0, correct? But surely I don't want it to produce a pitch when its 0, only when it is NOT 0?

When I tried that above snippet, when the soft pot wasn't pressed, the volume and resonance pin indeed no longer changed the pitch. Then when I changed the pitch by pressing the soft pot, it would produce a very low pitched note, and nothing else when moving up and down the ribbon

However, the delay between the two analogReads, while not stopping the issue of the pots changing the pitch, does stop them from changing the pitch too dramatically (ie - they only increase the pitch slightly, rather than what seemed like over an octave before)

Sorry I meant != not ==

While you seem to have mastered the quote icon you don't seem to have mastered the code icon just one to the left of it.

Hints
Take the reading and then do the action, do not do all the readings and then all the actions.
Why use the map function when all you need is to divide by eight which is just three shifts to the left.
MidiVal = analogRead(pin) << 3
In fact you don't even need that intermediate variable.

What did I say in my last post if this did not work?

The reasion why one pot reading affects the other is either high input impedance or bad wiring. How can anyone tell if you have bad wiring if you don't let them see it.