Coin (Or any object) counter

Hi guys,
I’m currently working on a different project, and I need to count little pieces of wood (around 80 of them). So I said - Why not put up a small object counter with arduino, a laser, and a photo-resistor?
The hardware is very simple, but I have problems with the software. This is the code that triggers a buzzer every time something interrupts the beam:

void setup() 
{
  pinMode(13, OUTPUT); 
} 
void loop()
  { 
if(analogRead(0) < 750){
  digitalWrite(13, HIGH);   
} 
else { 
 digitalWrite(13, LOW); 
  }
}

Pretty simple. So to count the coins (and show the result in the serial monitor), I thought of making a while loop that has the code inside, and +1 the counter every time the analogRead is below 750. The loop condition is some character put in the serial monitor.
I tried a lot of things but it doesn’t work. Help? Please?
Thanks a lot :slight_smile:

I tried a lot of things but it doesn't work. Help? Please?

What did you try? What actually happened? What did you expect to happen?

You need to look at the state change detection example. You don't want to count when the sensor IS active. You want to count when the sensor BECOMES active. That is what the state change detection example shows.

Well, I don't really know how to stop the loop when the serial gets a character, so I tried writing:

while (digitalRead(4) == HIGH)

And basically connecting pin 4 to 5V. I hoped that when I remove it from 5V, the loop will stop, but something else happend: The buzzer just beeped, all the time, without stopping, with no relation to the laser, the light sensor or pin 4. However, now that I think about it, I think it's better to stop the loop when the serial receives a char.

And why not count whenever the sensor is active? Where can I find this example? Thanks

Well, I don't really know how to stop the loop when the serial gets a character

Why do you need to?

I hoped that when I remove it from 5V, the loop will stop, but something else happend: The buzzer just beeped, all the time, without stopping, with no relation to the laser, the light sensor or pin 4.

We have no idea where you put that snippet, or what is in the body of the while statement, so you can't really expect any help. Perhaps the fine folks at http://snippets-r-us.com could help.

And why not count whenever the sensor is active?

Because the sensor may be active for several iterations of loop() while one piece passes by. How many times do you want to count the one piece?

Where can I find this example?

Are you serious? It's with all the others. File + Examples + 2. Digital + State Change Detection.

Ok guys, I’m really sorry for the stupidity, I have focused a little and things a bit more clear now. I based my latest code on the state change example, but it still doesn’t work:
What I tried:

int sensorState = 0;
int lastSensorState = 0;
int counter = 0;

const int buzzerPin = 13;
const int sensorPin = 0;

void setup() {
  pinMode(buzzerPin, OUTPUT);
  pinMode(sensorPin, INPUT);
  Serial.begin(9600);
}

void loop() {
  sensorState = analogRead(sensorPin);
  if (sensorState != lastSensorState)
  {
    if (sensorState < 750)
    {
      counter++;
      Serial.println("on");
      Serial.print("number of objects:  ");
      Serial.println(counter);
      digitalWrite(buzzerPin, HIGH);
      delay(200);
      digitalWrite(buzzerPin, LOW);
    }
    else 
    {
      Serial.println("off");
    }
  }
  lastSensorState = sensorState;
}

What happend:
It thought the sensor is interrupted all the time, and it was constantly on.
The circuit:
A photoresistor connected to ground through a 10K ohm resistor, and to analog pin 0;
a buzzer connected to pin 13;
a laser pointer.
Thanks for your patience :slight_smile:

  sensorState = analogRead(sensorPin);

You don't read the state of an analog pin. You read a value from the analog pin. So, what value are you reading? Why are you NOT printing it to the Serial Monitor so you KNOW what is happening?

  if (sensorState != lastSensorState)

Unlike digital pins, which return 0 or 1, the analog pins return values between 0 and 1023. Two consecutive readings can fluctuate 1 or 2 steps. This statement will be true more often than it will be false.

Thanks for the quick reply! How do you suggest I fix it? For some reason, it reads values between 1-5 from the sensor all the time, with no regards whether I shine the laser on the photoresistor or not.

For some reason, it reads values between 1-5 from the sensor all the time, with no regards whether I shine the laser on the photoresistor or not.

We need to see how you have the photoresistor wired.

It may need to be part of a voltage divider circuit. That would simply involve wiring a resistor from one end of the photoresistor to ground. Then, connect the common connection (where the two resistors come together) to the analog pin.

And, of course, making sure that the pin you are reading from IS the pin that the device is connected to.

This is the schematic:

What kind of laser are you using? The only thing I can think of is that the photoresistor is not triggered by light from the laser, because of frequency or color.

Well, it's red, but I can say for sure that the photoresistor is sensitive to that specific laser. I tried making it beep whenever the beam doesn't reach the photoresistor, and that worked: http://www.youtube.com/watch?v=SZf7t1YHkL8 I bet the problem is in the code.

I bet the problem is in the code.

But, obviously not in the code used in the video. So, where is that code? We can then compare the code in the video with the code you posted earlier (which looks OK), to see what the differences are.

Sure, this is the code used in the video (and was used as a reference to the new code):

void setup() 
{
  pinMode(4, OUTPUT); 
  pinMode(13, OUTPUT); 
} 
void loop()
{ 
    digitalWrite(4, HIGH);
    if(analogRead(0) < 750) {
      digitalWrite(13, HIGH);   
    } 
    else { digitalWrite(13, LOW); 
    }
}

Very simple code.

What is connected to pin 4? Is that the laser? If so, what is powering the laser in the original code?

It isn't necessary to set the laser pin HIGH on every pass through loop().

In the original code, get rid of the last state stuff (for now). Or, modify the second code to count only when the LED is to be turned on when it is not already on.

Oh sorry, that’s the old code, I don’t actually remember why I had pin 4 set on HIGH. The laser actually gets power from the 3V output on the Uno.
Here is the new code:

void setup() 
{
   pinMode(13, OUTPUT); 
} 
void loop()
{ 
    if(analogRead(0) < 750) {
      digitalWrite(13, HIGH);   
    } 
    else { digitalWrite(13, LOW); 
    }
}

Up... Anyone?

    if(analogRead(0) < 750) {

Store the value read in a variable. Compare that variable to a threshold, and set a boolean.

int val = analogRead(0);
boolean low = val < 750;
if(low && !lowlastTime)
{
   // count the object...
}
lowlastTime = low;

I really lost you there. In the current code, I don't know where to put the code you included. Where to state the variables? Where to define them? It's pretty much the same code done differently from the way I see it