Introduction: Bike Speedometer

I went to an REI garage sale a few weeks ago, and I picked up an awesome $50 bike speedometer for only $5! I often bike with a group of friends, and it is cool to see my speed in real time. It would be awesome if they could do the same, but none of us want to pay full price. This is what motivated me to try to make my own.

Step 1: Tools/Materials

Materials:

  • LCD
  • pcb kit (pcb board, acid, lines)
  • 3d printing filament
  • atmega 328
  • 16 MHz crystal
  • 2* 22 picofarad (ceramic) capacitors
  • power supply-4 AAA's
  • Solder
  • Spray paint
  • Super Glue
  • Acetone
  • Cotton Swabs

Tools:

  • 3d printer
  • Bread board
  • jumper cables
  • Soldering Iron
  • Laser cutter

Step 2: Bootload the Atmega 328 Chip

This first step is necessary to make this project small. Using an Arduino to process and display information for the bike speedometer makes the whole project much larger than necessary. I went about reducing size by removing the Arduino and replacing it with an Atmega 328 chip. This chip is the core of Arduino and, as a result, you can program them with an Arduino. There is no point in me trying and failing to fully explain the process in this instructable, so I will simply share the resources I used. I may make a bootloading instructables later.

Step 3: Upload Your Code to the Atmega 328

Uploading the code to the Atmega 328 is really easy. Once the bootloader is installed, switch the original 328 chip with the one that you just created. Press the reset button, and the onboard LED should flash. If it doen't, the bootloader was not correctly installed. Once you are sure it works, upload the code as normal. Then re-switch the chips back.

****I made a stupid mistake when putting the the 328 chip in the Arduino. Make sure you place it in the correct orientation. The arc on one end should be facing away from the cable and the power in. If you have any doubt, or it doesn't work, google an image of an Arduino and double check.



First Try



#include < LiquidCrystal.h >

volatile byte rpmcount;

unsigned int rpm;
unsigned int rpm2;
int mph;


unsigned long timeold;

LiquidCrystal lcd(12, 11, 5, 4, 3, 7);

void setup()
{
Serial.begin(9600);
attachInterrupt(0, rpm_fun, RISING);
lcd.begin(8, 2);


rpmcount = 0;
rpm = 0;
timeold = 0;
lcd.clear();
lcd.setCursor(0,0);
lcd.print("RPM:");
lcd.setCursor(0,1);
lcd.print("MPH:");
}


void loop()
{
if (rpmcount >= 4) {
//Update RPM every 4 counts, increase this for better RPM resolution,
//decrease for faster update
rpm = 30*1000/(millis() - timeold)*rpmcount;
timeold = millis();
rpmcount = 0;
rpm2 = rpm * 2;
mph= rpm2 * .0082070707; //the .0082... is from the [(circumfrance of your tire)(60)]/63,360
Serial.println(rpm2,DEC);
Serial.println(mph,1);


lcd.setCursor(0, 0);
lcd.print("RPM:");
lcd.setCursor(4, 0);
lcd.print(rpm2);
lcd.setCursor(0, 1);
lcd.print("MPH:");
lcd.setCursor(4, 1);
lcd.print(mph);


}
}


void rpm_fun()
{
rpmcount++;
//Each rotation, this interrupt function is run twice
}





Second Try



#include < LiquidCrystal.h >

volatile byte rpmcount;

unsigned int rpm;

unsigned long timeold;

LiquidCrystal lcd(12, 11, 5, 4, 3, 7);

void setup()
{
Serial.begin(9600);
attachInterrupt(0, rpm_fun, RISING);
lcd.begin(8, 2);


rpmcount = 0;
rpm = 0;
timeold = 0;


lcd.clear();
lcd.setCursor(0,0);
lcd.print("MPH:");


}


void loop()
{
if (rpmcount == 4) {
rpm = 49*100/(millis() - timeold)*4;
timeold = millis();


Serial.println(rpm);


lcd.setCursor(4, 0);
lcd.print(rpm);



rpmcount = 0;
}
}


void rpm_fun()
{rpmcount++;
//Each rotation, this interrupt function is run twice
}

Step 4: Prototype

After getting the Atmega ready, it is time to test everything. Put together the parts on a breadboard. This is a crucial step to ensure success. The images are some of the resources I used and the prototypes I made.

Step 5: Build the Sensor

The speed sensor consists of a hall effect sensor and a resistor. This goes in a 3d printed plastic shell that can be found here. Solder the hall effect sensor to the resistor and that to three wires. Put heat shrink tubing on the individual wires, and then on all three. Put the assembly in the 3d printed housing and fill it with hot glue. Be careful to not fill the channel for the zip ties with hot glue. Put double sided tap on the sensor housing to ensure it does not slip.

Step 6: IC Socket

I did not have a 28 pin IC socket. So I made my own. I started with two 16 pin IC sockets and cut the end off of one. I cut off the last 4 pin holes to minimize size. After reducing the size to match the Atmega 328, I removed the pins that I did not need. My reasoning behind this was to reduce errors. I surface mounted the chip, and if there were a bunch of terminals laying around it could short circuit.

Step 7: PCB V1

Using the layout above, engrave your PCB.

  1. Lay down the lines and the dots and all that good stuff.
  2. Etch the board in acid for 20-60 minutes.
  3. Rinse in water to stop the reaction.
  4. Lightly sand the black lines off with steel wool.

Step 8: PCB V2

I could not get v1 to work, so I made a second version. I could not get v2 to work either. When I found the problem with v2 I looked at v1 and it was the same problem. I switched some connecting wires. A stupid problem that took hours to find and fix.

Making the PCB is really quite easy and simple.

  1. Design the PCB in some software. I used Inventor 2016.
  2. Paint the copper clad board.
  3. Laser cut the design on some wood to make sure it works. If it does, move on to step 4.
  4. Position the painted copper over the laser cut wood, and re-cut the pcb. Doing so will guarantee correct positioning.
  5. Cut and then sand the PCB to the correct size.
  6. Place the PCB in the etching fluid and stir often.
  7. Remove the etched PCB, and run water over it to stop the reaction.
  8. Drill holes where needed.
  9. Using steel wool, remove the paint.

Step 9: Solder

Solder on the components using the sketch to identify where parts go. One problem I made twice was switching "4" and "3." I am not sure why, but be careful when you do it.

Step 10: Speedometer Housing

Start by modeling the cover. As usual, you can find mine here. I decided not to worry about water proofing, as I store my bike under an awning and rarely ride in the rain. I designed the cover to be a thin and low profile as possible.

  • Design the cover
  • Print the cover
  • Sand the cover
  • Glue the zip ties on
  • -optional- Using cotton swabs, apply some acetone to darken the color (I would not do this again, I liked the finish without acetone more)

Step 11: The End

Thanks for reading this instructables. I hope you enjoyed it. I learned a LOT creating this bike speedometer. If you think this is a cool project, vote for me in the motion and micro controller contest.

Comments

author
toutoune (author)2017-05-09

Hello, first, thnak you a lot for your instrtables. It is the first ever i read about bike speedometer, and you taught me about the hall effect sensor.
But I am not sure to understand why there is no magnet attached to some of the spokes, and how your sensor is rated and taken into acount by your code.
Does it detect every spoke that passes by, which means you then divide the frequency of detection by the number of spokes to get the rpm ?

author
zposner (author)toutoune2017-05-10

It only detects one spoke. You can think of the spoke as just one point on the wheel, so each time it passes you know the wheel has made 1 full revolution. Then, if you know the circumfrance of the tire, you can do some math to figure out how far you have traveled.

author
toutoune (author)zposner2017-06-10

OK, thanks. So does it not mean you put a magnet on this spoke ? And in this case, did y you glue it ?

author
gsmhack (author)2017-04-27

Hi, I think you should check that code you posted!

author
zposner (author)gsmhack2017-04-27

Whats wrong? I do have an updated code, but it exludes rpm because i couldnt get it to work

About This Instructable

1,943views

39favorites

License:

Bio: We're born, we make, and we die. So start making!
More by zposner:Rocket StandTimeless BraceletTube Patch
Add instructable to: