CSCI 381: Embedded Systems Design

Propeller Clock

by Matt J. and Ryan B.

This project was inspired by the Open Display project. The LEDs would now be used to display an analog clock, with second, minute and hour hands. This is obtained by using 8 dual color LEDs and then one additional LED, for the hour marker, and rotating them. We can do this by rotating the board the LEDs are on, and turning the LEDs on and off in the correct positions to get the clock. We also wanted to add the ability to change time, so we added 2 buttons to the back of the board.

Video
clip
AVI ~4.1Mb

Hardware

The design is essentially the same as the Open Display project; using a small motor to rotate a PCB board. We salvaged the motor from a rotating pumpkin toy available from Walgreens. The motor is powered by ~2V, and we stabilize this by a voltage regulator, LM317, in a standard way. It runs at approx. 4200 RPM from 3V with no load. The most viable components on the board are the LEDs (Dual Color & Blue Color), but magic takes place behind them. The board is based off the PIC16F648A from Microchip.

Schematic PCB design

We wanted to include in design the ability to change the time when needed. This was done by adding two switches to the board. We originally were worried if they would be too large for the board, but the switches are quite small. The component that allows us to keep time accurately is the 32,768kHz Crystal. This allows us to increment time in 1 second intervals (more on this later in the software section). A Hall Effect sensor is used to start the display of the clock over at 12:00, similar to the sensor used in the open display, only we needed ours to be in the exact spot. If not, our clock would appear to be off. The sensor picks up input from a magnet mounted on the bracket. The inputs are used as an external interrupt input for the PIC.

While working on the design, we noticed that the LEDs would be getting 1/60th of their normal power, due to the rapid switching from on to off. The max output from the PIC is 25mA and with the LEDs having a current rating of 20mA, we would have very dimm LEDs. We went with having 4 MOSFET transistors, in packs of 2 each. These allow us to supply a peak current of 130mA to the LEDs, which is close to the max of 140mA. The ability to turn the power on and off is also supplied. If we did not use those, the output supplied by the PIC would not be enough to sufficiently light the LEDs brightly, for the short burst. This allowed us to have bright LEDs, and a simpler design for the LEDs.

Front view Back view Top view

While working on the design, we noticed that the LEDs would be getting 1/60th of their normal power, due to the rapid switching from on to off. The max output from the PIC is 25mA and with the LEDs having a current rating of 20mA, we would have very dimm LEDs. We went with having 4 MOSFET transistors, in packs of 2 each. These allow us to supply a peak current of 130mA to the LEDs, which is close to the max of 140mA. The ability to turn the power on and off is also supplied. If we did not use those, the output supplied by the PIC would not be enough to sufficiently light the LEDs brightly, for the short burst. This allowed us to have bright LEDs, and a simpler design for the LEDs.

The configuration of the LEDs was done for a few reasons. There are 3 arms we need to display: hour, minute and second. If we output 0 to RC2 & 4, we get the minute hand; RC0 & 1 for second, and RC0 & 4 for hour. In addition, all the components are surface mounted, except the LEDs. We cut a hole down the middle of the board where the LEDs go. This allowed us to surface mount the LEDs on the backside, and the upper part of the LED show through the board. Knowing we would have to program the chip multiple times, we also implemented the chips programming pins, so we could program it after installation to the board.

The problem which made us think the most was getting power to the board. We used metal brush device from the rotating pumpkin toy. The brush is used to conduct plus, and ground is reached through the shaft of the motor and the motor housing. The brush is attached on the side of an aluminum bracket, allowed us to perform the same function as the brushes in the Open Air Display project. This bracket was then mounted on a wooden block for a finished look.

Brushes Magnet & sensor Assembled PCB

Software

On startup, the initialization of the variables, and external interrupt input are done, as well as an external clock setup. We also start off by clearing all position variables for hours, minutes, seconds, the tick, hour marker position (tickNotch) and increment the hour marker variable by 1. At this point, we move into the main loop.

The main loop first clears the display by outputting '010111' to PORTC. We output logical 1 to turn the display off because of the MOSFET chips we implemented in the design. Then we first check to see if a tickNotch needs to be displayed. If subtracting leads to the Z bit being set, we turn on the tickNotch, or blue LED for this position, and then proceed to setup tickNotch with 5 again. If not, we proceed to check for displaying the second, minute and hour hands.

loop                            ; main loop starts here
    movlw   b'010111'           ; shut down display
    movwf   PORTC
    
    decfsz  tickNotch, f        ; set the Z flag accordingly
    goto    $+4
    bsf	    PORTC, 3            ; turn on tick mark	
    movlw   5
    movwf   tickNotch           ; tickNotch = 5
    
    movf    seconds, w
    subwf   tick, w
    btfss   STATUS, Z
    goto    check_min
    
    bcf     PORTC, 0            ; display seconds arm
    bcf     PORTC, 1
    
check_min
    movf    minutes, w
    subwf   tick, w
    btfss   STATUS, Z
    goto    check_hours
    
    bcf     PORTC, 2            ; display minutes arm
    bcf     PORTC, 4
    
check_hours
    movf    hrpos, w
    subwf   tick, w
    btfss   STATUS, Z
    goto    $+3
    
    bcf     PORTC, 1            ; display hours arm
    bcf     PORTC, 2
    
    call    delayOn             ; ON delay
    movlw   b'010111'           ; shut down display
    movwf   PORTC
    call    delayOff            ; gap delay

    incf    tick, f             ; update the tick counter
    movlw   60
    subwf   tick, w
    btfss   STATUS, Z
     goto   loop

setTime                         ; wait for interrupt
    call    wait4Release        ; wait 32msec for button release
    call    wait4Press          ; wait 32msec for button press	
    goto    setTime	

After computing whether the LEDs are on or off, we move to the delay between events. We shut down the display, perform the gap delay, and update the tick position. The delayOn and delayOff methods determine the width of the gap. The delay between them is about 400 microseconds, resulting in 400·60 = 24 milliseconds clock refresh rate, or 42Hz refreshing frequency. We chose this as a compromise between display flickering and motor noise, which increases at higher rotations. Then if the tick position is 60, we go to the button status checking loop, and wait for an interrupt either from the TMR1 timer, or Hall sensor.

The ISR performs 2 functions, either recalls start, or processes a pulse from the crystal. If the interrupt is from the crystal, we setup the next interrupt and increment the variable seconds. We proceed to increment minutes = seconds (mod 60) and clear seconds. Calculating the hour hand position is next, by multiplying hours by 5, and then adding floor(minutes/12). We came up with 5 because 60 divided by 12 is 5. For every hour, the hour hand needs to move 5 positions. Example: If it is 3:36, thats 3·5 = 15. So we need start the position of the hour hand at 15, or 3:00. The floor(minutes/12), gives us how much farther we need to move the hour hand past 3:00. So, 36/12 = 3. So we have 15 + 3 is 18. The hour hand needs to be displayed when we reach the 18th position. Finally, if minutes equal 60, we update hours, etc.

...
    btfss   PIR1, TMR1IF        ; TMR1 interrupt?
    goto    start               ; NO - process the synchro pulse
    
    movlw   128                 ; set next timer interrupt event
    movwf   TMR1H               ; 1 sec apart

    incf    seconds, f          ; put the ISR main code here
    movlw   60
    subwf   seconds, w
    btfss   STATUS, Z
    goto   ISR_end
    clrf    seconds             ; seconds = seconds (mod 60)
    incf    minutes, f
    movf    hours, w			
    movwf   hrpos               ; hrpos = hours
    addwf   hrpos, f
    addwf   hrpos, f
    addwf   hrpos, f
    addwf   hrpos, f            ; hrpos = hours * 5

    movf    minutes, w
    movwf   temp
    movlw   12                  ; hrpos += floor(minutes/12)
    incf    hrpos, f	
    subwf   temp, f
    btfsc   STATUS, C	
    goto   $-3
    decf    hrpos, f

    movlw   60
    subwf   minutes, w
    btfss   STATUS, Z
    goto   ISR_end

    clrf    minutes             ; minutes = minutes (mod 60)
    incf    hours, f
    movlw   12
    subwf   hours, w
    btfss   STATUS, Z
    goto   ISR_end		
    clrf    hours               ; hours = hours (mod 12)
...

The final parts of code are for button processing of 2 tactile push buttons. We catch the button presses while waiting for an interrupt, as in the code above. We first check for a button release, if a release is found, we pause 4096·8, or 32msec. Checking it again confirms the button press, and not just a bouncing of the button. From there, we process either a minute or hour button. We increment minutes and hours similarly to how we do it above. To give the user a visual confirmation the time has been updated, we blink the blue LED.

Final thoughts

After working with two devices that use similar construction, the rotating boards design needs an improvement if this device is to have long term use. The board itself is out in the open and could get damaged. For version II, we would mount the board on a hard drive motor. This would allow for the whole design to be more flat.

With the current device, enclosing it in plastic is the best option for longevity. Also, use as bright LEDs as possible, and use them at maximum pulse current to get the brightest illumination.

Parts list

Downloads


Last modified:Mon, Jan 23, 2023.

13042