Hello all,
First of all thanks for the help i have found on this forum, its a great source of info.
Secondly i thought i would share my code to read my chinese digital verneer caliper. I have found lots of examples out there, but couldn't see a complete code for this type. Also i dont claim for one minute that i have (or could) write this code from scratch - it is more of a combination of lots of other peoples code as found on the net.
If anyone has advice of code improvement please let me know.
The caliper is the type that sends a single 24bit word of the structure described here -
I boutght mine from Chronos in the UK.
I hope this is of use to people.
Next i would like to expand it to read multiple calipers. I'm told that its possible to enable more than the standar 2 interrupts on a uno..... i'll put my investigating hat on.
Thanks again.
// code by mbconfuse 29/05/11
#include <avr/interrupt.h>
volatile int bumper;
int clockPin = 2;
int dataPin = 4;
int counter = 0;
const int numberBits = 24;
int data[numberBits];
int usedData[numberBits];
int decimalVal = 0;
int oldDecimalVal = 0;
int passedSync=0;
void setup()
{
Serial.begin(9600);
pinMode(clockPin, INPUT);
pinMode(dataPin, INPUT);
attachInterrupt(0, bumperISR, FALLING);
interrupts();
bumper = 0;
}
void bumperISR()
{
char sample = 0;
if(digitalRead(clockPin) == LOW) sample++;
if(digitalRead(clockPin) == LOW) sample++;
if(digitalRead(clockPin) == LOW) sample++;
if(sample > 2)
bumper = 1;
}
void loop()
{
// make sure loop starts at the begining of the data set
syncronization();
//start that data conversion
if (bumper == 1 && passedSync ==1)
{
//sample the reading 3 times
data[counter] = sampleData (digitalRead(dataPin), 1);
bumper = 0;
counter++;
if(counter >=numberBits)
{
// tick the syncronisatoin button
passedSync = 1;
counter =0;
//reverse the order of the binary bits
reverseData();
//printBinary();
//convert the binary to decimal
binaryToDecimal(usedData, numberBits);
}
}
}
// convert a binary string to a decimal number, returns decimal value
void binaryToDecimal(int TheArray[], int numBits)
{
int b, k, m, n;
int len;
//start bit and end bit are chosen to chop out the unwanted bits
int startBit = 3;
int endBit = 22;
len = numBits;
for(k = startBit; k <= endBit; k++)
{
n = TheArray[k];
if ((n > 1) || (n < 0))
{
Serial.println("non_binary number!!");
}
for(b = 1, m = endBit; m > k; m--)
{
// 1 2 4 8 16 32 64 ... place-values, reversed here
b *= 2; //same as b = b * 2
}
decimalVal = decimalVal + n * b;
}
//only print if the decimal value has changed
if (decimalVal != oldDecimalVal)
{
Serial.print("Decimal =");
// the 3rd bit is the positive/negative bit. if it is 1 then value is negative.
if(TheArray[2] == 1)
{
Serial.print(" -");
}
Serial.println(decimalVal);
oldDecimalVal = decimalVal;
}
decimalVal = 0;
}
//sample data three times
int sampleData(int readData, int highLow)
{
char sample = 0;
if(readData == highLow) sample++;
if(readData == highLow) sample++;
if(readData == highLow) sample++;
if(sample > 2)
{
return(highLow);
}
else return((1-highLow));
}
//reverse all the binary bits
void reverseData()
{
int k=0;
for(int j = (numberBits-1) ; j >= 0; j--)
{
usedData[k] = data[j];
k++;
}
}
//print the binary
void printBinary()
{
for (int i = 0 ; i < numberBits; i++)
{
Serial.print(usedData[i]);;
}
Serial.println("");
}
//sync so we start at the begining of a data set
//320 is approx lenght of gap between data sets
void syncronization()
{
if(bumper == 1 && passedSync == 0)
{
int time;
do
{
time = pulseIn(clockPin, HIGH);
} while(time < 320);
passedSync = 1;
Serial.print("time - ");
Serial.println(time);
delay (320);
bumper =0;
}
}