IR counter project question

Hello all, I am very new at this and I have started a beer can counter project, borrowing code from someone who wrote a person counter project on Gadgetronicx. Everything is working except that the IR is counting 2 for a motion towards the sensor and 2 for motion away from it which is creating an incorrect total for object counting. Can anyone assist with this?

Here’s what I’ve got

#include <LiquidCrystal.h>

LiquidCrystal lcd (8,7,6,5,4,3);
unsigned int count=0;
char converted_value[6];

void setup(){
  lcd.begin(16,2);
  lcd.print("CAN COUNT:");
  attachInterrupt(digitalPinToInterrupt(2),counter,HIGH);
}

void loop()
{
 lcd.setCursor(0,1);
 lcd.print(converted_value);
}

void counter()
{
  count++;
  sprintf(converted_value,"%d",count);
}

Can_counter_200112.ino (401 Bytes)

If the IR counts 2 all the time, the easy fix is to divide that by 2 and get the 1 You want.

Its technically counting 4 per movement. I have a feeling its an easy fix but I can not find a solution.

Do not use delay()s or do printing in ISRs.

Do these back in loop().

Make ‘count’ volatile.

Better still do not us interrupts, also use the millis() technique ‘BWD’ (blink without delay) instead of delay()s.

Unless @larryd helps You, divide by 4 then.

 attachInterrupt(digitalPinToInterrupt(2),counter,HIGH);

HIGH is not correct, and if you look at Arduino.h file you see that you are really attaching a CHANGE mode interrupt.

#define HIGH 0x1
#define CHANGE 1

I suspect you are triggering an interrupt on both edges of a signal.

This isr is wrong. delay() does not work within an interrupt. It relys on other interrupts which are disabled within the isr. Count does appear to increment, but the use of the comma operator is likely to cause you problems.

void counter()
{
  //count++, delay(100);
   count++;
  //sprintf(converted_value,"%d",count);
}

That looks a real clean "fix".

I’m getting inconstant results and I’m still getting an interrupt count on both edges as you stated. I’m still unsure how to avoid the double count and get a more consistent count. I’m not sure I followed your suggestion properly but check it out. Keep in mind I am very new at this.

The delay() was left in by my mistake from earlier attempts to repair before I realized my error.

I appreciate the help!!

#include <LiquidCrystal.h>
#define HIGH 0x1
#define CHANGE 1
LiquidCrystal lcd (8,7,6,5,4,3);
unsigned int count=0;
char converted_value[6];

void setup(){
  lcd.begin(16,2);
  lcd.print("CAN COUNT:");
  attachInterrupt(digitalPinToInterrupt(2),counter,CHANGE);
}

void loop()
{
 lcd.setCursor(0,1);
 lcd.print(converted_value);
}

void counter()
{
  count++;
  sprintf(converted_value,"%d",count);
}

Try this:

#include <LiquidCrystal.h>

LiquidCrystal lcd (8, 7, 6, 5, 4, 3);

unsigned long lastMillis;
unsigned int lastCount    = 1;
unsigned int count        = 0;

byte lastState;

char converted_value[6];


//*********************************************************************
void setup()
{
  Serial.begin(9600);

  lcd.begin(16, 2);
  lcd.print("CAN COUNT:");

  pinMode(2, INPUT_PULLUP);
  lastState = digitalRead(2);


} //END of setup()


//*********************************************************************
void loop()
{
  //************************************
  //time to check the IR sensor?
  if (millis() - lastMillis >= 10)
  {
    //restart the timer
    lastMillis = millis();

    checkIRsensor();
  }

  //************************************
  //update the LCD only if there is a change in the 'count'
  if (lastCount != count)
  {
    lastCount = count;

    sprintf(converted_value, "%d", count);

    Serial.println(converted_value);

    lcd.setCursor(0, 1);
    lcd.print(converted_value);
  }

} //END of loop()

//*********************************************************************
void checkIRsensor()
{
  byte currentState = 0;

  //************************************
  currentState = digitalRead(2);
  if ( lastState != currentState)
  {
    lastState = currentState;

    if (currentState == HIGH)
    {
      count++;
    }
  }

} //END of checkIRsensor()

BTW

Why are you doing this?

sprintf(converted_value, "%d", count);

Larryd you are a life saver! It seems to be working perfectly now. Thank you very much for you help!