Go Down

Topic: Help scaling values for MIDI velocity with piezo transducers. (Read 876 times) previous topic - next topic

assemblyworker

Hi there,

I'm trying to figure out a way of adapting a code so I get sensible velocity readings using piezo transducers.

I'm working on a code by Amanda Ghassaei and whilst it works fine for a single transducer,  I can't find a way to make it work for multiple transducers.

The code is as follows...

Code: [Select]

int noteOn = 144; //turn note on
int noteOff = 128;//turn note off
int piezo1 = A0; // analogue pin 1m ? resistor
int piezo2 = A1; // analogue pin 1m ? resistor
int piezo3 = A2; // analogue pin 1m ? resistor
#define cal 130 //set delay time

int threshold = 20; // sets threshold for trigger


void setup(){
  Serial.begin(9600);//baud rate
}
void loop(){



  int piezoVal1 = analogRead(piezo1);//assign piezo1
  if (piezoVal1>threshold){
    int maxPiezoVal = getMaxVal(piezoVal1);
    byte velocity = map(maxPiezoVal, 0, 1023, 50, 127);//scale piezo reading to MIDI values
    MIDImessage(noteOn, 60, velocity);
    delay(cal);
    MIDImessage(noteOff, 60, 0);
    delay(50);
  }

  int piezoVal2 = analogRead(piezo2);//assign piezo2
  if (piezoVal2>threshold){
    int maxPiezoVal = getMaxVal(piezoVal2);
    byte velocity = map(maxPiezoVal, 0, 1023, 50, 127);//scale piezo reading to MIDI values
    MIDImessage(noteOn, 63, velocity);
    delay(cal);
    MIDImessage(noteOff, 63, 0);
    delay(50);

  }

  int piezoVal3 = analogRead(piezo3);//assign piezo3
  if (piezoVal3>threshold){
    int maxPiezoVal = getMaxVal(piezoVal3);
    byte velocity = map(maxPiezoVal, 0, 1023, 40, 127);//scale piezo reading to MIDI values
    MIDImessage(noteOn, 65, velocity);
    delay(cal);
    MIDImessage(noteOff, 65, 0);
    delay(50);
  }

}
// serial data output to hairless MIDI
void MIDImessage(byte command, byte data1, byte data2){
  Serial.write(command);
  Serial.write(data1);
  Serial.write(data2);

}

//sets scaling for MIDI velocity
int getMaxVal(int lastVal){
  int currentVal = analogRead(piezo1);
  while (currentVal>lastVal){
    lastVal = currentVal;
    currentVal = analogRead(piezo1);
  }
  return lastVal;

}




The part in particular is the last section that deals with getting the last value reading from the piezo and using that for the scaling.

Code: [Select]

//sets scaling for MIDI velocity
int getMaxVal(int lastVal){
  int currentVal = analogRead(piezo1);
  while (currentVal>lastVal){
    lastVal = currentVal;
    currentVal = analogRead(piezo1);
  }
  return lastVal;

}




How can I make this work for each individual transducer, I have tried a few ways but always end up with error messages as soon as I add the other pins.

Many thanks.

Grumpy_Mike

Quote
How can I make this work for each individual transducer,

Use an array to hold the new and old readings and cycle through the array with a for loop.

GreenPhantom

I read this post.  But it hit me that coincidentally I am seeking information on how to build a keyboard switch contact circuit for measuring the force applied to the switch to generate note velocity.  But how do the piezo transducers work?

Grumpy_Mike

They respond to a change in their shape produced by an impact or vibration by producing a voltage.
http://en.wikipedia.org/wiki/Piezoelectric_sensor
They are not really suitable for measuring the force on a key because after the initial impact the voltage output drops to nothing. Therefore they will not tell you anything about how hard the keys are held down only how fast they are hit.

The other thing is they need an analogue input and to measure the peak of the very sharp pulse produced from these sensors you need some conditioning electronics on each one. This makes the circuit more complex especially if their are a lot of keys. And it also requires some analogue multiplexing to scan and measure these pulses.

Go Up