2 direction device; one way 12 seconds timer, other way speedtrap

Hi fellow experimentalists!

I'm trying to develop a device for a motorcycle course, that starts a 12 seconds timer when riding in one way and measures the speed of the motorcycle when passing in the other direction.

The passing is captured by 2 IR sensors.

The problem i'm facing is that the timer and speedtrap works...as long there only 1 interruption of the sensors...
Since motorcycles have 2 wheels...the problem starts.

The timer gets interrupted and I can't figure out how to fix this.
I'm looking and trying to find a way that the arduino looks only at the first signal, when the front wheel passes, so it ignores the second passage of the rear wheel.

...but without further results...

maybe someone can help me figure this out?

Thank you!

Not sure, even after reading the forum, if i need to paste my code just underneath this text.


#include <Arduino.h>

int RelayPin = 7;           //relay on pin 7
int SpeedPin = 8;           //drukknop activatie snelheidsmeting op 8
int TimerPin = 6;           //drukknop activatie 12" op 6



#include <Wire.h>               // Library for I2C communication
#include <LiquidCrystal_I2C.h>  // Library for LCD

LiquidCrystal_I2C lcd = LiquidCrystal_I2C(0x27, 16, 2); // Change to (0x27,16,2) for 16x2 LCD.

//const int rs = 12, en = 11, d4 = 5, d5 = 4, d6 = 3, d7 = 2; //toewijzing pinnen lcd
//LiquidCrystal lcd(rs, en, d4, d5, d6, d7);      //iets voor LCD

int Timer_buttonState      = 0;     // current state of the button
int Speed_buttonState      = 0;     // current state of the button
int lastTimer_buttonState  = 0;     // previous state of the button

int RelayState           = 0;     // remember current relai state
int loadState_1        = 1;

int count = 12;                //initial value counter
int switch_var = 0;            //switch varon 0



void setup() {

 
 lcd.init();
 //lcd.backlight();
 
 pinMode(RelayPin, OUTPUT);    //output relay
 pinMode(TimerPin, INPUT);     //input sensor start 12"
 pinMode(SpeedPin, INPUT);     //input sensor speedtrap


 lcd.clear();                  //prepare display
 lcd.setCursor(1,0);
 lcd.print("Snelheidsmeter");
 lcd.setCursor(5,1);
 lcd.print("klaar");

}

void loop() {

 

 
 Timer_buttonState = ! digitalRead(TimerPin);     // read the pushbutton input pin
 Speed_buttonState = ! digitalRead(SpeedPin);

   int photo_light_1;      //variabele light_1
   int photo_light_2;      //variabele light_2
   unsigned int time_1;    //variabele time_1
   unsigned int time_2;    //variabele time_2
   float elapsedTime;      //variabele elapsed time
   float spd;              //variabele speed
   unsigned int afstandSensor; //variabele distance between sensors
    

   time_1 = 0;             //set initial timing to 0
   time_2 = 0;
   afstandSensor = 805;    //set distance sensors

 

//sensor that gets activated first

 

 if (Timer_buttonState == 1)
   {
    
    switch_var = 1;    //start timer
    
   }
 else if (Speed_buttonState == 1)
 {
   switch_var = 2;     //start speedtrap
 }

 
 
 switch (switch_var)
 {
  
   case 1:

 
     if (Timer_buttonState == 1 && lastTimer_buttonState == 0) 
     {
       loadState_1++;
   
     if (loadState_1 > 2) loadState_1 = 1;       // 2 states as it is now
         RelayState = 1 - RelayState;              //RelayState will alternate between 1 and 0
      
         digitalWrite(RelayPin, RelayState);       //Variabele activeren RelayState
         //delay(100);                      
         digitalWrite(RelayPin,HIGH);            //activeren relai bij activeren 12"
         delay(100);
         digitalWrite(RelayPin,LOW);             // relai uitschakelen
         
         
      }
   
     //delay(50);                          //noise cancelling button
   
    lastTimer_buttonState = Timer_buttonState;      //onthouden stand van knop
   
 
       if (RelayState == 1)
           {                   //wanner knop hoog wordt mag de 12" timer beginnen

           lcd.clear();
           lcd.setCursor(5,0);
           lcd.print("Timer :");             //op eerste lijn "timer" zichtbaar maken
           lcd.setCursor(8,1);                 //lcd 2de rij aanspreken
           lcd.print("Sec");                 //Plaats "Sec" op tweede rij
           lcd.setCursor(5, 1);                //activeren waar seconden zichtbaar gemaakt worden
           lcd.print(count);                   //zichtbaar maken seconden
           delay(1000);                    //1 seconde wachten
           count = count -1;               //aftellen
   
  
   
         if (count == 0)  {                  //wanneer teller op 0 led laten/zoemer branden
     
      
        digitalWrite(RelayPin,HIGH);     //activatie led
        //delay(2000);
        //digitalWrite(RelayPin, LOW);     // led uitschakelen
        Timer_buttonState = 0 ;
         }
         
      if (count < 0)
         {                     //Teller tot 0 laten aftellen
           RelayState = 0;
           //digitalWrite(RelayPin,HIGH);     //activatie led
           //delay(100);
             digitalWrite(RelayPin, LOW);     // led uitschakelen
           count = 12;                   //resetten teller
           delay(3000);
           lcd.clear();
           delay(1000);
           lcd.setCursor(1,0);
           lcd.print("Snelheidsmeter");
           lcd.setCursor(5,1);
           lcd.print("klaar");
       }
   }
 break;

   case 2:

     if (Speed_buttonState == HIGH)
     {

 photo_light_1 = ! digitalRead(SpeedPin);

 if (photo_light_1 == HIGH)
   {
     time_1 = millis();
     
     Serial.print("time 1");
     Serial.println(time_1);

     while(true)
     {
     photo_light_2 = ! digitalRead(TimerPin);
     
       if (photo_light_2 == HIGH)
       {     
      time_2 = millis();
      Serial.print("time 2");
      Serial.println(time_2);

       elapsedTime = (time_2 - time_1);
       Serial.print("elapsed time ");
       Serial.print(elapsedTime);
       Serial.println(" sec");
       delay(200);
       spd = (afstandSensor/elapsedTime);

       Serial.print("Snelheid  ");
       Serial.println(spd);
       delay(200);

       lcd.clear();
       lcd.setCursor(4,0);
       lcd.print("Snelheid");
       lcd.setCursor(3,1);
       lcd.print(spd);
       
       lcd.print(" km/h");
       delay(5000);
       lcd.clear();
       delay(1000);
       lcd.setCursor(1,0);
       lcd.print("Snelheidsmeter");
       lcd.setCursor(5,1);
       lcd.print("klaar");
       



      
     // break;
       }  
     }
   }
     }
 //break;  

}
}

12_seconden_timer_v2.cpp (5.69 KB)

12_seconden_timer_v2.cpp (5.69 KB)

I'm looking and trying to find a way that the arduino looks only at the first signal, when the front wheel passes, so it ignores the second passage of the rear wheel.

At what point does the rear wheel pass? Before the second sensor is activated or after?

If you want to ignore the rear wheel completely, you may be able to insert a lock (additional variable) on the first sensor, which will be undone only when the second sensor is activated. And add a minimum interval for the next operation.

Hi rtek1000! Thank you for your quick answer!

That sounds as a possible solution!
The distance of the rear wheel to the front can vay depending on the type of motorcycle.
But the idea of ignoring the rear wheel seems to be a good solution.

The timer and speedtrap are activated from the front wheel, so i don't need any signal of the rear wheel.

Do you have an example or what code do i need to use to insert a lock?

It is not very difficult to understand (and write the code) just think that for you to be able to block a comparison (IF) it is enough that one of the parts is false.

var1 = 0

if (sensor1 is true) && (var1 is 0)
var1 = 1
else (sensor2 is true) && (var1 is 1)
var1 = 0

(note: the code above is illustrative only)

Hi There!

I figured it out...Today i tested it with an actual motorcycle passing by...
only one strange thing occured where I don't have any logic explaination to it.

It's about the timing captured doesn't make sense...i'll try to explain...

Bike is passing by around 30 km/h...the arduino results to 44 km/h.
but...when the bike passes at 40 km/h the arduino gives 92km/h

the calculation of the conversion is correct...it's just the timeframe created by the two sensors is getting me confused...

some details...
the distance between sensors is 0,805m
in theory, at 30 km/h the time would be 0,0966 s
what i measured was 0,0645 s...

and at 40km/h time is 0,07245s
arduino measured 0,0312s

So i'm kinda stuck here...would you know what the cause can be?

Thank you!

#include <Countimer.h>      //load from Countimer from library
#include <Wire.h>               // Library for I2C communication
#include <LiquidCrystal_I2C.h>  // Library for LCD

LiquidCrystal_I2C lcd = LiquidCrystal_I2C(0x27, 16, 2); // Change to (0x27,16,2) for 16x2 LCD.
Countimer tDown;            //use the countdown function

//INPUTS
int TimerPin = 6;         //Sensor detection start Timer
int SpeedPin = 8;         //Sensor detection SpeedTrap

//OUTPUTS
int BuzzerPin = 7;        //Buzzer output

//VARIABLES
int TimerPinState = 0;    //Variable TimerPinState set to 0
int SpeedPinState = 0;    //Variable SpeedPinState set to 0
int Var = 0;              //Variable Var set to 0
double Distance = 0.805; //Distance between the two sensors
int ShowSpeedTime = 1000; //The amount of time the speed is displayed before resetting in ms
double Time_1 = 0;
double Time_2 = micros();
double Speed = 0;
double ElapsedTime = 0;

//-----------------------------------------------------------------------
void setup() {
  // put your setup code here, to run once:
Serial.begin(9600);       //serial monitor
lcd.init();               //initiate LCD

//SET IN AND OUTPUTS
pinMode(TimerPin, INPUT);   //Declare TimerPin as Input
pinMode(SpeedPin, INPUT);   //Declare SpeedPin as Input
pinMode(BuzzerPin, OUTPUT); //Declare BuzzerPin as Output

tDown.setCounter(0, 0, 12, tDown.COUNT_DOWN, tDownComplete); //set counter to 12s    
tDown.setInterval(print_time2, 1000);                       //set Interval of countdown

  lcd.clear();                  //prepare display
  lcd.setCursor(1,0);
  lcd.print("Snelheidsmeter");  //show snelheidsmeter when ready
  lcd.setCursor(5,1);
  lcd.print("klaar");           //show klaar when ready                 
}
//-----------------------------------------------------------------------
void loop() {
  // put your main code here, to run repeatedly:
TimerPinState = !digitalRead(TimerPin);   //Read value of TimerPin
SpeedPinState = !digitalRead(SpeedPin);   //Read value of SpeedPin
tDown.run();            //Run countdowntimer

/*
//----- SERIAL MONITOR
Serial.print(" in 1: ");
Serial.print(TimerPinState);
Serial.print(" in 2: ");
Serial.print(SpeedPinState);
//Serial.print("  Var: ");
//Serial.print(Var);
Serial.print(" Tijd: ");
//Serial.print(tDown.getCurrentSeconds());
////Serial.print(" buzz: ");
//Serial.print(digitalRead(BuzzerPin));
Serial.print(" T_1: ");
Serial.print(Time_1);
Serial.print(" T_2: ");
Serial.print(Time_2);
*/Serial.print(" ELA: ");
Serial.print(ElapsedTime);
Serial.print(" Spd: ");
Serial.print(Speed);
Serial.println();



    
//CHOICE BETWEEN TIMER AND SPEEDTRAP 
  if ((TimerPinState == HIGH) && (Var == 0) && (Var != 88))   { //at rest, if the timerpin gets activated set var to 1
              Var = 1;                                  //if true sets var to 1
                                                }
 
  else if ((SpeedPinState == HIGH) && (Var == 0) && (Var != 99)) { //at rest, if speedpin gets activated set var to 2
             Var = 2;                                  //if true sets var to 1
                                                               }
//CASE
  switch (Var)   {   //case setup
      case 1:           //case 1 sets var to 99 til countdown is completed
        lcd.clear();
        Var = 99;                 //Set var to 99
        tDown.start();           //Start CountDown
        Short_Alert();           //gives buzzer a short HIGH as start of countdown
      break;

    case 2:
        if (!digitalRead(SpeedPin) == HIGH) {
          Time_1 = micros();
            while(!digitalRead(TimerPin) == LOW)  {
                  Time_2 = micros();
                  ElapsedTime = ((Time_2 - Time_1)/10000);
                  Speed = ((Distance/ElapsedTime)*360);
                  if (Speed < 10){
              lcd.clear();
              lcd.setCursor(3,0);
              lcd.print("TE TRAAG !");
              delay(5000);
              break;
          }
                  ShowSpeed();
                  Var = 88;
                    Serial.print(" Tijd: ");
                    Serial.print(ElapsedTime);
                    Serial.print(" Spd: ");
                    Serial.print(Speed);
                    Serial.print(" Var: ");
                    Serial.print(Var);
                    Serial.println();
                    //Var = 0;
                                        }
                                                      }
          
          if (Var == 88){
                      delay(3000);
                      Var = 0;
                   }
           break;
                   }//END OF SWITCH CASE
  
 
//INFORMATION ON LCD     
      if (Var == 99) { //While countdown is activated, show countdown on LCD display
          lcd.clear();
          lcd.setCursor(5,0);
          lcd.print("Timer");
          lcd.setCursor(3,1);
          lcd.print(tDown.getCurrentSeconds());   //show seconds
          lcd.setCursor(6,1);
          lcd.print("Sec");
          delay(1000);
                    }
      else {       //in rest show text
           
           }



}
//END OF VOID LOOP   

void tDownComplete()  {      //when countdown is completed
  digitalWrite(BuzzerPin,HIGH); //Set buzzer to HIGH
  delay(750);                   //Keep HIGH for 750ms
  digitalWrite(BuzzerPin,LOW);  //Set buzzer to LOW
  lcd.clear();
          lcd.setCursor(5,0);
          lcd.print("Timer");
          lcd.setCursor(3,1);
          lcd.print(tDown.getCurrentSeconds());   //show seconds
          lcd.setCursor(6,1);
          lcd.print("Sec");
          delay(1000);
  Var = 0;                  //set var back to 0
  //lcd.clear();
                      }
void print_time2(){ }

void Short_Alert() {           //Activation for short Alert
  digitalWrite(BuzzerPin,HIGH); //Set buzzer to HIGH
  delay(50);                    //Keep HIGH for 50ms
  digitalWrite(BuzzerPin,LOW);  //Set buzzer to 0
                    }

void ShowSpeed()  {
          lcd.clear();
          lcd.setCursor(4,0);
          lcd.print("Snelheid");
          lcd.setCursor(5,1);
          lcd.print(Speed,0);
          lcd.setCursor(9,1);
          lcd.print("Km/h");
                    }