' Make-it-with-Micromite (Part 11)

'

' Electronic Combination Lock (MIWM_ECL.txt)

'



' SETUP

' -----



Option autorun on ' ensure program runs automatically

CLS               ' clear IPS display



Dim keys(16)      ' array to store the state of each key (0=pressed)

Dim KeyPressed    ' numeric value of the last key pressed

Dim integer Col1,Col2 ' the current Bright and Dim LED colour values

Dim d1,d2         ' LED 'Flash' rate (d1=On time, d2=On+Off time)



w=30              ' pixel width of LED/box that is 'flashed' on IPS

pwd$="1,2,3,4"    ' this is the valid password

epw$=""           ' epw$ stores the 'Entered PassWord'. Clear it



kVcc=9            ' I/O pin that connects to keypad: Vcc

kGND=10           ' I/O pin that connects to keypad: GND

kClk=17           ' I/O pin that connects to keypad: SCL

kDat=18           ' I/O pin that connects to keypad: SDO



Pin(kClk)=1       ' configure SCL to be high (i.e. active Low)

SetPin kClk,dout  ' set SCL pin as output (and initially High)

SetPin kGND,dout

SetPin kVcc,dout

Pin(kVcc)=1

SetPin kDat,inth,myInt ' set interrupt to detect a valid keypad press



keyPad_Reset      ' call SUB to reset display for a new keypad entry





' MAIN PROG       ' uses Timer value to simulate a flashing LED on IPS

' ---------       ' Interrupt when keypad pressed - changes LED colour



' d1,d2, Col1, Col2 set in SUB myInt to alter LED colour & flash-rate





Do

  If Timer<d1 Then ' see if Timer value is within LED 'On' time

    Box (MM.HRes-w)/2,(MM.VRes-w)/2,w,w,0,0,Col1   ' draw Bright LED

    Pause 5

  Else

    If Timer<d2 Then  ' if here then see if within 'On+Off' time

      Box (MM.HRes-w)/2,(MM.VRes-w)/2,w,w,0,0,Col2 ' draw Dim LED

      Pause 5

    Else

      Timer=0         ' if here On+Off time exceeded so reset timer

    End If

  End If

Loop





' SUBROUTINES

' -----------



Sub myInt           ' this SUB is called whenever a Pad is pressed (or released)

  KeyPressed=0           ' clear value 'KeyPressed' of the last Pad pressed

  For x = 1 To 16        ' read all 16 Pads

    Pulse kClk,0.01        ' pulse SCL low to trigger KeyPad to output Pad state

    keys(x)=Pin(kDat)      ' read state of Pad 'x' into keys() array

    If keys(x)=0 Then KeyPressed=x  ' 0 on kDat indicates Pad pressed

  Next x                 ' read all 16 Pad states (only one will be low if pressed)

  If keypressed>0 Then     ' if KeyPressed=0 then key just released (so do nothing)

    If Len(epw$)>0 Then      ' if NOT first Pad-press of an entry, then add a comma

      Print ",";               ' print comma on Console (to separate last pad value)

      epw$=epw$+","            ' add comma to EnteredPassWord (epw$)

    End If

    Print Str$(KeyPressed);  ' print Pad value on console

    epw$=epw$+Str$(KeyPressed) ' add Pad value to EnteredPassWord

    beepKeyPad               ' beep to indicate valid KeyPad pressed

    col1=RGB(255,128,0)      ' set Col1 to a Bright Orange value

    col2=RGB(32,16,0)        ' set Col2 to a Dim Orange value

    d1=300                   ' set relevant flash-rate for Orange LED

    d2=600

    SetTick 2500,kpTimeOut   ' reset the TimeOut timer (a SetTick) to 2500ms

  End If

  ChkPWD                   ' see if entered password matches the stored password

End Sub



Sub kpTimeOut     ' If this gets called, then time-up for entry attempt

  KeyPad_Reset      ' call SUB to reset the display (Red LED and slow pulse flash)

  BeepTimeOut       ' call SUB to sound an audible notification

End Sub



Sub KeyPad_Reset    ' reset Combination Lock

  Timer = 0                ' reset system-timer value (used to flash LED on IPS)

  SetTick 0,0              ' switch off (disable) entry-attempt (SetTick) timer

  d1=80                    ' set relevant flash-rates for Red LED

  d2=1500

  Col1=RGB(255,0,0)        ' set Col1 to a Bright Red value

  Col2=RGB(32,0,0)         ' set Col2 to a Dim Red value

  Box (MM.HRes-w)/2,(MM.VRes-w)/2,w,w,0,0,col1 ' immediately draw Bright LED 'box'

  epw$=""                  ' clear 'Entered PassWord' entry

  Keypressed=0             ' set last Pad pressed value to 0

  Print                    ' position console-cursor on a new line

End Sub





Sub BeepHi             ' sound a 15ms 1KHz Beep

  PWM 2,1000,100,50        ' sets 1KHz square-wave on PWM 2B (piezo +ve)

  SetPin(15),dout          ' set 0v on piezo -ve (piezo now sounds)

  Pause 15                 ' delay a bit (15ms)

  SetPin(15),off           ' switch off 0v on piezo -ve (piezo silent)

End Sub



Sub BeepLo             ' sound a 20ms 500Hz Beep

  PWM 2,500,100,50

  SetPin(15),dout

  Pause 20

  SetPin(15),off

End Sub



Sub BeepLong           ' sound a 100ms 2KHz Beep

  PWM 2,2000,100,50

  SetPin(15),dout

  Pause 100

  SetPin(15),off

End Sub



Sub BeepKeyPad         ' sounds a Tune whenever a Pad is pressed

  BeepHi

End Sub



Sub BeepTimeOut        ' sounds a Tune whenever attemp-entry times-out

  BeepHi

  Pause 50

  beepLo

  Pause 50

  beepLo

End Sub





Sub ChkPWD             ' SUB to check if Entered Password (epw$) is correct

    If epw$=pwd$ Then

      Pin(kVcc)=0          ' remove 3.3v power from KeyPad (avoids interrupts)

      SetPin kGND,off      ' remove 0v

      For x = 1 To 5       ' Flash a Green LED/box on the IPS (five times)

        Box (MM.HRes-w)/2,(MM.VRes-w)/2,w,w,0,0,RGB(0,255,0) ' Bright Green

        beepLong

        Box (MM.HRes-w)/2,(MM.VRes-w)/2,w,w,0,0,RGB(0,32,0)  ' Dim Green

        Pause 500

      Next x               ' flash five times

      Pin(kVcc)=1          ' re-apply 3.3v power back to KeyPad

      SetPin kGND,dout     ' re-apply 0v

      KeyPad_Reset         ' call SUB to reset things (Red LED and slow pulse flash)

    End If

End Sub