Nate Duxbury's Blog

Make all the things!

Breadboard Tachometer


Arduino Powered Tachometer built on a breadboard.

Arduino Powered Tachometer built on a breadboard.

After installing a 300W DC spindle on my shapeoko 2, I wanted to be able test the speed that the spindle was actually putting out. So I decided to build a simple tachometer to measure the RPM it was putting out.

It just so happened that we made something very similar in one of my engineering classes. In this class, we produced aluminum piston bodies to make a 6-cylinder rotary engine and it was actuated by pneumatic solenoids that were electronically controlled by an arduino and a reflective object sensor acting as an encoder. This encoder told the micro controller which of the input and output solenoids to activate in a specific order and thus ran the engine. The same sensor also recorded RPM of the engine, which is what I remembered and wanted to use for testing the speed of my DC spindle. I found a similar project online at and went from there.


Theory behind the device


A tachometer is a device to measure rotational speed of something. In this case, I wanted to measure rotational speed of my spindle motor on my CNC. To do so, the reflective object sensor is “tripped” once per revolution of whatever you are trying to measure. Basically, the sensor can tell if something is reflective or if something is not reflective. It does this by using an always on diode (IR I believe) on one side, and a photo transistor on the other side. If an object is reflective, the photo transistor can “see” the diode and gives that information back to the arduino. If an object is not reflective, the photo transistor does nothing, and that can be interpreted as a signal in itself. The code on the arduino can detect the changes from reflective to non-reflective and it can know the time between these events. Based on the time between the events, and the number of revolutions, the code gives back revolutions per minute (RPM). This information is then displayed on the LCD panel and is updated every cycle of the code.

For measuring the speed of my CNC spindle, the fan housing of the spindle rotates at the same RPM as the collet, and has a nice chromed surface that acts as my reflective surface. For the non-reflective surface, I just used a strip of blue painters tape.

Blue painters tape was used as the non-reflective surface that triggers the RPM sensor.

Blue painters tape was used as the non-reflective surface that triggers the RPM sensor.


Circuit Design


I followed the circuit design that I found on the site almost exactly. I followed the diagram from to build my own circuit, but I decided to change a few resistor values based on what I had available, but the main circuit is the same. I didn’t include the motor control circuitry that they did, since I wasn’t going to running any motors with this circuit.

I re-made the circuit diagram in Fritzing to show exactly how I made my circuit.

Breadboard Diagram of the Tachometer.

Breadboard Diagram of the Tachometer.

Circuit Diagram of the Tachometer sensor.

Circuit Diagram of the Tachometer sensor.




Parts List


Arduino Nano

16×2 LCD Display

Solderless Breadboard

OPB 742 reflective object sensor

9V Battery Clip

9V Battery

10k potentiometer

100 ohm resistor

68K ohm resistor

680 ohm Resistor

lots of random jumper wires




In the end I just used the exact code from the circuitstoday post. I tried to write my own based on the value of the sensor reading, but all I ended up with was a proximity sensor. It was always either too sensitive or not sensitive enough. I spent probably an hour or so learning how to analogRead the sensor value and how to display things on a 16×2 LCD, but once I tried the code from the circuitstoday post everything just worked.

For convenience, here is the a copy of the code direct from Again, this is NOT my code.

LiquidCrystal lcd(12,11,6,5,4,3);
int pwm=9;
int pot=A0;
float value=0;
int percent;
float rev=0;
int rpm;
int oldtime=0;
int time;

void isr() //interrupt service routine

void setup()
lcd.begin(16,2);                //initialize LCD
attachInterrupt(0,isr,RISING);  //attaching the interrupt

void loop()
detachInterrupt(0);           //detaches the interrupt
time=millis()-oldtime;        //finds the time 
rpm=(rev/time)*60000;         //calculates rpm
oldtime=millis();             //saves the current time
value=analogRead(pot);        //reads the speed control POT
analogWrite(pwm,value);       //sets the desired speed
percent=(value/255)*100;      //finds the duty cycle %
lcd.print(" RPM");
lcd.print("   ");






The tachometer did a fairly good job of reading RPM on my CNC spindle. It was sensitive to the distance to the surface it was measuring and the angle it was pointed at, but once it started reading, it worked quite well. The ergonomics of it being breadboard mounted were not the best, but it did work and it was readable.

This is how I held it while testing RPM.

This is how I held it while testing RPM.

This is how close the sensor was to the surface it was testing. Apologies for the blurry photo.

This is how close the sensor was to the surface it was testing. Apologies for the blurry photo.

I recorded an RPM of ~12360 for my DC spindle, which is very near what it should be operating at. (It is supposed to be 12000 RPM @ 48 VDC, which what it was set to).


Future Plans


I built this tachometer to verify that I was getting the correct speeds on my CNC spindle, but I have some other plans for it as well.

During my DC spindle installation, I had a lot of trouble with the spindle speed controller not accepting PWM speed commands near the upper limit of the PWM range. I could mess around with the range in the code, but I would have no way of telling what kind of RPM I was actually getting then. Now, I can measure the RPM that I am getting and correlate that to what I expected to get from software control.

Another thing I want to use this sensor for is closed-loop control of my spindle. Right now, my spindle control is open-loop. That is, I set the RPM of the spindle when I turn it on that is it. If the spindle gets bogged down cutting and RPM drops, my controller knows nothing and just keeps supplying the voltage for the RPM I set it at initially. With closed-loop control and a tachometer monitoring actual RPM on the spindle, a drop in RPM would be recognized and sent back to the controller and then the controller would send signals to correct for that RPM difference. There’s a lot of groundwork to be done to make this idea work, but I think it is very do-able.





All of the circuit design and code I copied from: “Tachometer using arduino”

Datasheet for the Reflective Object Sensor:

Getting the 16×2 LCD working, I followed the tutorial on :



5 thoughts on “Breadboard Tachometer

  1. what does the pot meter do in this circuit? i dont fully understand the reason behind it. it only lowers the resistant and nothing else right?

  2. Thanks for sharing this. I put it up on a breadboard and test it on my sherline. There were readings but the readings weren’t stable; it kept jumping around. When I hit max speed on the speed control pot, the LCD briefly displayed the max speed (rated 10000 rpm) and fell to about 1/2 of it (around 5000+ rpm). I was told that its because of noise in the input. Are you able to help with some suggestions on what I can do to eliminate that?

    • I cant really answer to the noise problem in the input, as I don’t really know the finer workings of the electrical components, but I do remember my own experiences when using this on a breadboard. It mattered very much how close the sensor was to the spinning part, and the angle that it was at relative to the surface. You want the sensor to be normal to the cylindrical surface (as opposed to tangent) and relatively close to the surface. Hope this helps!

      • Thanks for your quick reply.

        I’ll try orientation the sensor to face the pulley face then the much smaller spindle surface to see if that give cleaner signals.

Leave a Reply

Fill in your details below or click an icon to log in: Logo

You are commenting using your account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s