Use a pushbutton to calibrate an ADXL335 for an off level sisser table

I dialed in on my ADXL335 accuracy with my Arduino Uno and used it as a level sensor to level a home made scissor table.

What I would like to do is put in a momentary calibration button so when the table is on off-level ground, you can press the button and the table will level (while being used).

The following is a rundown of the project:

I built a scissor table using two 24inch linear actuators. Although the actuators are exactly the same, they don’t travel at the same speed. Using the ADXL335 I want to drop out one of the linear actuators using a relay to let the other actuator catch up and level the table. Then once the table is level, both actuators will work again.

Here is the code for dialing in the accelerometer to be an accurate tilt/level switch:

int groundpin = 18;    // analog input pin 4
int powerpin = 19;    // analog input pin 5
int xpin = 3;            // x-axis of the accelerometer
int ypin = 2;            // y-axis of the accelerometer
int zpin = 1;            // z-axis of the accelerometer
long y_max = 515;   // At level reading is 508 so min and max were inputed to set boundries.
long y_min = 507;

int relay = 13;        // pin 13 which will (through smaller relays), activate actuator relay.

long y = 0;

void setup()

{
  Serial.begin(9600);
  
  pinMode(relay, OUTPUT);
  
  pinMode(groundpin, OUTPUT);
  pinMode(powerpin, OUTPUT);
  digitalWrite(groundpin, LOW);
  digitalWrite(powerpin, HIGH);
}

void loop()
{
    y = analogRead(ypin);        // read analog pin 2 
    
    if (y < y_max) {               // if reading from analog pin 2 is less than 515
      
    delay (100);
    
    digitalWrite(relay, LOW);  // dont do anything
  
    Serial.println("The Table Is Level");
    
   
  } else if (y >= y_max) {       //if analog pin 2 is greater than 515
    
    digitalWrite(relay, HIGH); // turn on digital pin 13 (relay)

    Serial.println("The Table Is Tilted Right");
    
   }
}

The problem with this code is that if I move the table to off-level ground I would have to use a laptop to re-calibrate the ADXL335 to work in that position.
To remedy this problem I want to install a calibration button. So I rigged up a circuit where I put +5v to a momentary button to digital pin 7 and a 10kohm resistor to ground.
You would press the button, analog pin 2 would read the value of the y axis on the ADXL335 and sore that value. Then once the table started going up or down and goes up a value of greater than 5 of of the stored value then the relay will kick in and level the table out.

I had a crack at the code for this but it doesn’t do what I want it to do.

Digital pin 13 doesn’t go HIGH at all. Serial monitor doesn’t printout anything. When I press the momentary button, digital pin 13 goes HIGH and serial monitor prints out “The table is off level”!

int groundpin = 18; // analog input pin 4
int powerpin = 19;           // analog input pin 5
int xpin = 3;                   // x axis of the accelerometer
int ypin = 2;                   // y axis of the accelerometer
int zpin = 1;                   // z axis of the accelerometer

#define BUTTON 7         // button attached to digital pin 7
                
int val = 0;    
              
int relay = 13;               // digital pin 13 which will run the relay           

long y = 0;

void setup(){
  
  Serial.begin(9600);
  pinMode(BUTTON, INPUT);
  pinMode(relay, OUTPUT);
  
  pinMode(groundpin, OUTPUT);
  pinMode(powerpin, OUTPUT);
  digitalWrite(groundpin, LOW);
  digitalWrite(powerpin, HIGH);
}

void loop()
{
  val = digitalRead(BUTTON); //read digital pin 7
  
  if (val == HIGH) {               // if button is pressed read analog pin 2
    
    y = analogRead(ypin);       // store value of y axis 
    
    if ( y > y + 8)                  // if the value of the stored value is greater than 8
    
     delay(500);
    
    digitalWrite(relay, HIGH); // Turn on digital pin 13 (relay)
  
    Serial.println("The Table Is Off Level");
  
  } else {
    
    digitalWrite(relay, LOW); // Don't do anything!
  
  
  } if (y < y + 8) {
    
    digitalWrite(relay, LOW);

    Serial.println("The Table Is Level");
    
  } else  { 
    
    digitalWrite(relay, LOW);
  
    }

}

Any help with this would be greatly appreciated!

What is this if statement supposed to do ?
Will y ever be greater than y + 8 ?
What would happen even if it were ever true ?

    if ( y > y + 8)                  // if the value of the stored value is greater than 8
        delay(500);
    digitalWrite(relay, HIGH); // Turn on digital pin 13 (relay)
    Serial.println("The Table Is Off Level");

What does it actually do

How is your switch wired? Are we chasing a hardware problem or a software problem? Printing the state of the switch seems like the obvious thing to do to know whether the switch is working as intended.

Hi UkHeliBob,

The if statement is suppose to use the stored value after using the button to obtain a level value. It would compare the real time values being read then if the real time value goes greater than 8 of the stored value the relay would drop out one of the linear actuators and level the table. My trouble is that I will never have a known numeric value as the table will be moved on different unlevel surfaces thats why I am trying to write things like " if Y = Y+8" instead of " if Y = >450 && < 458.
I chose the value of 8 as a start. I could make that number smaller to make the switch more sensitive but I will have to play around with that once the gear is mounted onto the table. When I run the code I can store the value but then when I tilt the accelerometer, the arduino does not activate the relay when it should.

Regards Mathew

PaulS,

I am not confident with my code. I can store a value using the push button but not activate anything when the accelerometer is off tilt. What I do is place the ADXL335 resting from my bench onto a matchbox so it is sitting on an angle. I then hit the calibrate button to tell the arduino that this is 'my level'. then I move the ADXL335 on it's Y axis to see if an LED lights up (in place of the relay), and nothing happens. I have made a tilt sensor with the ADXL335 to light up an LED when off tilt so I think that the hardware is ok I'm just not confident that the code I wrote will have the outcome I am after.

Regards Mathew

Suppose for now that y equals 450 when the button is read
Your test then becomes

if (450 > 458)

That will never be true, nor will it be true for any value of y or for any positive value added to it

Judging by your comment

    if ( y > y + 8)                  // if the value of the stored value is greater than 8

what you need is

if (y > 8)

but are you sure that you are comparing the value read with the right variable ? You cannot have two variables with the same name in the same scope.

Great that helps a lot. I will have a go at altering the code and see if I have any luck.

Cheers.