issue with axis

Hello,

I am trying to use an axis module as a sensor for an alarm (movement detection). When the values (z,x,y) change it triggers a relay.

Here is my code to check it. I use "calibration" function in order to set the "Starting" position and min max limits. If the relay triggers (it detects some movement) it must calibrate again in order to check if the movement was momentary or permanent. The problem with my code is that after the first trigger the relay keeps triggering....

PS sorry if my code is not very good but I am a newbie. :confused:

#include <HMC5883L.h>
#include <Wire.h>

HMC5883L compass;

const int anoigma = 2;
const int kleisimo = 3;
const int buzzPin =  12;
int buttonState = 0;
int buttonState1 = 0;
int onState = 0;
int offState = 0;
int tiltval;
int relay = 5;
int relaytimer;

//Accelerometer limits
int xMin; //Minimum x Value
int xMax; //Maximum x Value
int xCal; //Calibrated x Value
int xCur; //Current x Value

int yMin; //Minimum y Value
int yMax; //Maximum y Value
int yCal; //Calibrated x Value
int yCur; //Current x Value

int zMin; //Minimum z Value
int zMax; //Maximum z Value
int zCal; //Calibrated x Value
int zCur; //Current x Value


int tolerance = 40;



const int ledPin =  13;
int ledState = LOW;
unsigned long previousMillis = 0;
const long interval = 1000;


void setup() {
  pinMode(buzzPin, OUTPUT);
  pinMode(anoigma, INPUT);
  pinMode(relay, OUTPUT);
  Serial.begin(9600);
  pinMode(ledPin, OUTPUT);

}




void loop() {
  digitalWrite(relay, HIGH);
  buttonState = digitalRead(anoigma);
  if (buttonState == HIGH) {

    calibration ();



    digitalWrite(buzzPin, HIGH);
    delay(50);
    digitalWrite(buzzPin, LOW);
    delay(50);
    digitalWrite(buzzPin, HIGH);
    delay(50);
    digitalWrite(buzzPin, LOW);
    delay(50);
    digitalWrite(buzzPin, HIGH);
    delay(50);
    digitalWrite(buzzPin, LOW);
    delay(600);
    digitalWrite(buzzPin, HIGH);
    delay(50);
    digitalWrite(buzzPin, LOW);
    Serial.println("anoikse");
    onState = 1;
    do
    {
      unsigned long currentMillis = millis();
      if (currentMillis - previousMillis >= interval) {
        // save the last time you blinked the LED
        previousMillis = currentMillis;

        // if the LED is off turn it on and vice-versa:
        if (ledState == LOW) {
          ledState = HIGH;
        } else {
          ledState = LOW;
        }

        // set the LED with the ledState of the variable:
        digitalWrite(ledPin, ledState);
      }
      // Serial.println("trexei while");

      Vector raw = compass.readRaw();
      xCur = raw.XAxis;
      yCur = raw.YAxis;
      zCur = raw.ZAxis;





      if (xCur > xMax || xCur < xMin || yCur > yMax || yCur < yMin || zCur > zMax || zCur < zMin)
      {
        Serial.println("tsoup");
        relaytimer = 0;
        alarm();
      }

      buttonState1 = digitalRead(kleisimo);
      if (buttonState1 == HIGH) {
        onState = 0;
      }
    } while (onState == 1);
    digitalWrite(buzzPin, HIGH);
    delay(50);
    digitalWrite(buzzPin, LOW);
    delay(50);
    digitalWrite(buzzPin, HIGH);
    delay(50);
    digitalWrite(buzzPin, LOW);
    delay(50);
    digitalWrite(buzzPin, HIGH);
    delay(50);
    digitalWrite(buzzPin, LOW);
    digitalWrite(ledPin, LOW);
    Serial.println("ekleise");

  }
}

void alarm()
{
  while (offState == 0) {
    digitalWrite(relay, LOW);
    buttonState1 = digitalRead(kleisimo);
    relaytimer++;
    //Serial.println(relaytimer);
    delay (10);
    if (buttonState1 == HIGH) {
      offState = 1;
    }
    if (relaytimer > 1000) {
      offState = 1;
    }
  }
  digitalWrite(relay, HIGH);
  offState = 0;
  calibration ();
}

void calibration ()
{
  //calibration
  Vector raw = compass.readRaw();
  Serial.print(" Xraw = ");
  Serial.print(raw.XAxis);
  xCal = raw.XAxis;
  xMin = (xCal - tolerance);
  xMax = (xCal + tolerance);
  Serial.print(" xMin = ");
  Serial.print(xMin);
  Serial.println(" xMax = ");
  Serial.print(xMax);

  Serial.println("\n");

  Serial.print(" Yraw = ");
  Serial.print(raw.YAxis);
  yCal = raw.YAxis;
  yMin = (yCal - tolerance);
  yMax = (yCal + tolerance);
  Serial.print(" yMin = ");
  Serial.print(yMin);
  Serial.print(" yMax = ");
  Serial.print(yMax);

  Serial.println("\n");
  Serial.print(" Zraw = ");
  Serial.print(raw.ZAxis);
  zCal = raw.ZAxis;
  zMin = (zCal - tolerance);
  zMax = (zCal + tolerance);
  Serial.print(" zMin = ");
  Serial.print(zMin);
  Serial.print(" zMax = ");
  Serial.print(zMax);
  Serial.println("\n");
}

I use "calibration" function in order to set the "Starting" position and min max limits. If the relay triggers (it detects some movement) it must calibrate again in order to check if the movement was momentary or permanent.

So, what is the problem? The code does something. You expect it to do something. All that we can surmise is that if the two things were the same thing, you wouldn't have needed to post.

I can understand what you mean....

my problem is that if the relay triggers for first time it is supposed to "calibrated" in the second position and trigger only if it moves again. My code keeps triggering my relay even if I dont move it for a second time.

my problem is that if the relay triggers for first time it is supposed to "calibrated" in the second position and trigger only if it moves again.

Does the calibrate function get called? If so, what do xMin, xMax, YMin, yMax, etc. get changed to?

yes. The function is called and the min max are getting changed each time with vallues like these:

Xraw = -287.00 xMin = -327 xMax = -247

Yraw = 173.00 yMin = 133 yMax = 213

Zraw = -98.00 zMin = -138 zMax = -58

I'm wondering how effective your calibrate routine is, seeing as how it only reads the compass once. I'd expect to read it over a period of time, and average the readings.