I have been reading this forum since almost two months ago and I like the fact it is for BUDGET lights. I like budget flashlights because I like to play with them replacing leds and drivers, something I won't do with expensive flashlights. The expensive flashlights I have are collecting dust just because I almost don't use them.
Considering some people here is wanting to use PIC microcontrollers I am posting this information I posted some time ago in another flashlight forum.
I have written and tested this PICAXE source code to implement multi-level functionality in DX SKU 15880 or any driver using Microchip PIC12F629 microcontroller.
The test was done using a regular LED instead in the actual driver. It must work in the actual driver.
You need to replace the stock microcontroller with a PICAXE-08M Surface Mount AXE007MSM device. You will also need to do some pin swapping and lifting since PICAXE-08M uses pin 5 to do PWM and DX SKU 15880 uses pin 7.
I used PICAXE mainly because there is no necesity for a programmer to burn the program into the device. A computer with a serial port (or USB to RS232 converter) and 2 resistors is all needed to program the device.
For more PICAXE information visit PICAXE's site.
This is the program's source code:
'LED PWM Driver software.
'Writen by Juan C Galvez
' the following EEPROM entry contains the desired level percentages
' The first entry contains the level position to use the next time the driver is powered.
' Next are the desired level percentages.
' The last position next to the last desired level must be zero. It is used as end indicator
' Example EEPROM entries:
' 1, 1, 50, 100, 0 means 1%, 50%, 100%
' 1, 10, 100, 0 means 10%, 100%
' 1, 10, 30, 50, 100, 0 means 10%, 30%, 50%, 100%
' No SOS nor STROBE implemented.
EEPROM 0,(1, 5, 50, 100, 0 )
symbol LEVEL_SHIFT_PERIOD = 3000
' b0 keeps the current level positi b0 = b0 & $0F
' bit7 If 0 then keep the current level. If 1 then go to next level. Note: bit7 if the MSB in field b0
' b1 Current level value (%)
read 0,b0 ' Read next level position
if bit7 = 0 then ' If bit 7 not set the keep the current level.
read b0, b1 ' Read current level value
else
b0 = b0 & $0F ' Turn bit 7 off before reading position value
do
b0 = b0 + 1 ' Go to next level
read b0, b1 ' Read next level value
if b1 = 0 then ' If next level value is zero then start over.
b0 = 0 ' Reset position
end if
loop while b1 = 0 ' Keep until a valid position has been
end if
bit7 = 1 ' Turn bit 7 on. This means that the next time the driver must go to the next level
write 0, b0 ' Write the value to EEPROM position 0
w1 = b1 * 4 ' Multiply level value times 4
pwmout 2 , 99, w1 ' Turn the LED using the current/calculated level
pause LEVEL_SHIFT_PERIOD ' Wait n seconds
bit7 = 0 ' Turn bit7 off so the next time the driver is powered it will keep the current level
write 0, b0 ' Write current level position to EEPROM
b0 = 1 ' Enter an infinite loop
do
pause 2000 'Used to allow firmware upgrade while running.
loop while b0 = 1
As written, the code implements 3 brightness levels 5%, 50% and 100% but that can be easely changed. Also, the level change occurs if the driver is powered for 3 seconds; I mean, if you turn the driver on and keep is for at least 3 seconds then the next time you turn the driver again it will start in the last used time. I you turn the driver on and turn it off before 3 seconds then the driver will use the next level the next time it is turned on. To change this 3 seconds just modify the line containing:
symbol LEVEL_SHIFT_PERIOD = 3000
with the milliseconds you want to use.
I hope this code is useful to some one.
Juan C.