/* Program Description: This program controls an LED light engine used as a brake light on a motorcycle. When the brakes are applied the tail light flashes several times off then on before being a steady on brake light. The program also has a feature to disable the flashing brake light and the brake light will behave like a standard lamp ie no flashing. This mode is enabled ( flash mode disabled ) by turning the motorcycles key on while holding the brake on. The state is reset after a power cycle. Legal Note: I read the entire vehicle code for my state. It does not address brake light flashers, but does prohibit " rotating, oscillating or flashing red lights ". I believe a brake light flasher differs from " rotating, oscillating and flashing " lights in the implied duration of operation. My state did not respond to emails I sent requesting clarification. Basically, modify your vehicle at your own risk. Change Log 2012.4.21 - added 1 mS debounce to brake switch in main loop - Pete A circuit description and other details can be found at http://petemills.blogspot.com Filename: led_brakelight_main.c Author: Pete Mills petemills.blogspot.com 2012.4.15 Int. RC Osc. 8 MHz; Start-up time PWRDWN/RESET: 6 CK/14 CK + 64 ms */ //********** Includes ********** #include <avr/io.h> #include <util/delay.h> //********** Definitions ********** // Output to LED Light Engine #define LED PB0 #define LED_PORT PORTB #define LED_DDR DDRB // Input for Brake Switch #define BRAKE_SWITCH PINB4 // bit is clear when brake switch is pressed #define BRAKE_SWITCH_PORT PINB #define BRAKE_SWITCH_DDR DDRB // PWM Preset Values #define TAIL_LIGHT_PWM 25 #define BRAKE_LIGHT_PWM 255 //********** Function Prototypes ********** void setup( void ); void brake_alert( uint8_t number_of_flashes ); //********** Global Variables ********** uint8_t disable_flash = 0; // if 1, the flashing part of the brake light will be disabled int main(void) { setup(); _delay_ms( 5 ); // if the brake light is held on during boot up, disable the flashing // flashing can only be disabled during boot up ( key on ) and is reset after power down ( key off ) // this could be useful if you suddenly learn your flashing light is causing a problem for other motorists // or citizens employed to monitor the adherence to legislation and cite violations for deviation from such if ( bit_is_clear( BRAKE_SWITCH_PORT, BRAKE_SWITCH ) ) { disable_flash = 1; } while(1) { if ( bit_is_clear( BRAKE_SWITCH_PORT, BRAKE_SWITCH ) ) // if the brakes are applied { _delay_ms( 1 ); // filter time aka debounce if ( bit_is_clear( BRAKE_SWITCH_PORT, BRAKE_SWITCH ) ) // if the brakes are actually applied { // if we are allowed to flash, do if( disable_flash == 0 ) { brake_alert( 5 ); } // if the brakes are still applied, hold the LED light engine to a brighter output // until you release the brakes while( bit_is_clear( BRAKE_SWITCH_PORT, BRAKE_SWITCH ) ) { OCR0A = BRAKE_LIGHT_PWM; } _delay_ms( 100 ); // debounce the brake switch release ( break ) } } OCR0A = TAIL_LIGHT_PWM; // restore the tail light on /* // demo mode for( ;; ) { brake_alert(6); OCR0A = BRAKE_LIGHT_PWM; _delay_ms(2000); OCR0A = TAIL_LIGHT_PWM; _delay_ms(4000); } */ } } //********** Functions ********** void setup(void) { //********* Port Config ********* LED_DDR |= ( 1 << LED); // set PB0 to "1" for output LED_PORT &= ~( 1 << LED ); // turn the led light engine off BRAKE_SWITCH_DDR &= ~( 1 << BRAKE_SWITCH ); // set BRAKE_SWITCH pin to 0 for input BRAKE_SWITCH_PORT |= ( 1 << BRAKE_SWITCH ); // write a 1 to BRAKE_SWITCH to enable the internal pullup //********** PWM Config ********* TCCR0A |= ( ( 1 << COM0A1 ) | ( 1 << WGM01 ) | ( 1 << WGM00 ) ); // non inverting fast pwm TCCR0B |= ( 1 << CS00 ); // start the timer } void brake_alert( uint8_t number_of_flashes ) { // here we create a visual alert that the brakes have been applied // pass this function the number of flashes desired ( off then on = 1 ) //uint8_t delay_between_flashes = 50; // for video demonstration purposes ( video aliasing issues ) uint8_t delay_between_flashes = 25; // every day use uint8_t alert_pwm_min = 2; // minimum and max values to flash between during the alert uint8_t alert_pwm_max = 255; for( int i = 0; i < number_of_flashes; i++ ) { OCR0A = alert_pwm_min; _delay_ms( delay_between_flashes ); OCR0A = alert_pwm_max; _delay_ms( delay_between_flashes ); } }

UPDATE:This project was so overwhelmingly well received that it has spawned a commercial interest. The version available for purchase varies somewhat in it's flash patterns and also in the ability to record and play back your own flash patterns. If you would like to check it out take a look at Betelgeuse - A Programmable LED Brake Lamp at my new company Lakeside Electronics, LLC.I Purchased a motorcycle about two weeks ago. Interestingly, whenever I tell someone this news, they immediately proceed to tell me the most gruesome injuries and stomach turning plights that they or someone they know, has fallen victim to while motorcycling. In some cases, these raconteur's briefly pause to look over their shoulder, presumably scanning for small children or otherwise offendable ears, before delivering the goriest details.One commonality in these stories, aside from the macabre and arguably poor timing involved in telling them to me is that many accidents come down to a lack of visibility of motorcycles and their riders. Less than Argus-eyed motorists often pull out into the path of a motorcycle and with insufficient time for evasive action, that quickly an accident has occurred. Other times, drivers may focus on the car ahead of the motorcycle and in the event of stopping at a red light or similar, fail to leave enough room for the motorcycle, unfortunately rear ending him or her.In the photo below, you can see that I am in one piece and the bike is also. Let's see what we can do to help keep things that way.To partially combat the lack of visibility I decided to make a replacement brake light for my bike; one that would strobe briefly when I applied the brakes then stay solid on. I got this idea when I noticed a similar strobing effect to the brake lights on an ambulance that I was following near to, but not immediately behind. Those lights really got me to notice the ambulance which I had largely ignored up until that point.I would also want a way to be able to disable the brief flash before the brake light stays solid on. This could be useful if the flash was ever to cause a safety hazard to other drivers or if I am ever stopped by the police for having this system I can easily disable the strobe part and still have a functioning brake light; I do not want to be stranded. I wrote the software so that if you turn the key on while you have the brakes applied, the flash is disabled. You must turn the key off, then back on, without the brake applied to restore the flash functionality.Here is a video of the prototype Tenty LED Brake Light installed and operating. In the video, I demonstrate the flashing brake light 3 times and then key off. Then I disable the strobing part by turning the key on while holding the brake on, demonstrate that several times and key off again. Finally I re-enable the strobing functionality by key on with the brake off. For the purposes of the video, I lengthened the duration of the flash on and off times. This is so the camera can better capture the flashes.In order to keep this system reversible should I ever have the need to put it back to stock, here is how I mounted the circuit board inside the tail light lens. I bought some replacement bulbs at a local auto parts store, broke out the glass and desoldered the filament. I replaced the filament by soldering wires to the tail light power, brake light power and ground. I ran a file over the solder blobs just enough to level them out so they would make good contact with the socket. I then filled the bayonet base with epoxy and inserted an 8-32 stainless steel screw into the base being careful not to touch the screw to any metal, accidentally making the screw a conductor. Below are a few pictures of this process.After installing the modified bayonet screw mounts I threaded two nuts on each and jammed them together. This is what the back of the circuit board will rest on. You can see several pictures of the final assembly below.Circuit:The circuit is basically a large array of really bright red LED's ( Light Engine ) and an ATTiny85 microcontroller to tell the LED light engine how to behave. There are also two high brightness LED's that shine downward onto the license plate. They are solid on all the time as required by the Michigan vehicle code. The red LED's , made by Optek have a 100 degree viewing angle and output 8000 mlm each - there are 16 of them. The brake light switch delivers it's ~12 V signal translated thru an 2n3904 transistor to pull a microcontroller pin low. I usually use 14.4 V when doing calculations for operating voltage on 12V systems like this. Total current draw with all LED's at maximum brightness is less than 500 mA. I ordered the logic level mosfet IRLU3410PBF from mouser.com also, which is used for the PWM control of the light engine. Below you will find a screen cap pic of the schematic.SoftwareThere are two modes of operation to this brake light - flashing and non flashing. The non flashing brake light is activated by turning the key on while holding the brake and behaves just like a stock brake light would. Flashing mode is enabled by default so key on with brake off and you are good to go. In this mode, the LED light engine strobes briefly upon initial application of the brake then is a steady on light. I set the period of the flashes to be higher for the videos so the camera could pick them up, you can see in the code below that the flash period is twice as fast in the operational version of the software. Feel free to use the code as you see fit.Legal Note:I'm not too sure what to say about the legality of this project. I read the entire vehicle code for my state. There was no reference to brake light flashers for cars or motorcycles. The vehicle code for Michigan does prohibit " rotating, oscillating or flashing lights " on non-emergency vehicles, however I believe my brake light does not qualify as the clear intent in the vehicle code was " rotating, oscillating or flashing " lights that continue to do so for an extended period of time as emergency or police vehicles do. Really, my device is no different than tapping your brake pedal several times before stopping your motorcycle. In the end, I did send an email to the state of Michigan requesting clarification. At the time of this writing there has been no response. I think the bottom line is, don't modify your vehicle unless you are willing to accept full responsibility for any outcome.Here are a couple pictures of the build process. The abstract looking pictures are of the LED light engine shining thru my desk magnifier onto the ceiling.