Enabling the robot to recharge it's own batteries was something I wanted to get done sooner rather than later. One of the primary reasons for this is that it meant I needed to periodically switch back to the default firmware if I wanted to charge up the batteries. The second reason though, was that it was a very appropriate stepping-stone on the way to getting several other features working.
You see, the atmel 128 Analog to Digital Converter has a built in multiplexer which allows the single peripheral to measure up to eight different voltage nodes relative to ground potential or other nodes, at various levels of gain. Even better, these sources and configurations are software selectable by the use of a 5-bit multiplexer.
If all that sounded like technobabble to you, the long and the short of it is that the same basic code which measures the power left in the batteries can be used to get distance readings from the IR sensor, and sound input from the microphone!
But back to the power level sensor. This version of the code uses the debug info LED configuration to report the current level of the battery. If your robot is not plugged in, you can actually see the voltage drop when PF1/2 are pressed and the servos are moving. This is achieved by setting the multiplexer ADMUX to channel ADC1, and enabling the AD conversion complete interrupt in ADCSRA, which saves the voltage to the global location gA2D. It is only occasionally necessary to know the voltage, so conversion requests are triggered manually (as opposed to continuously) by setting the ADSC bit.
Recharging is enabled by setting bit 4 on PORTB, which digitally connects the battery to the external power source. Pressing and holding PF1 and PF2 for 2.5 seconds enters recharge mode, which trickle charges the NiMH batteries. Because I'm paranoid after the previous incident, the default setting is to only charge the robot for 10 seconds at a time. If you want to fully charge the batteries, pressing PF1 while the robot is charging will keep the batteries charging indefinitely.
"But Alex!" hear you cry. "If you can measure the voltage, why not simply disable charging when it's maxed out?"
Unfortunately, it's not that simple. When the external power source is present, the RBC automatically changes over the V++ supply to the power pack and becomes the voltage source. This means that whenever the plug is in, the value of gA2D will be that of the power source - even when the battery is low. I haven't figured out a way around this - you might also have noticed that there is no automatic recharge cut-off for the default firmware either.
The code is here. I'm looking for a better hosting service, but in the meantime, remember the click the "free" tab.
Robobob: Life of the party | Bear necessities | One step at a time | It's Alive!! | It was only a matter of time... | All work and no play | Two steps forward... | Computers 101 | Computers 102 | Computers 103