Advertisement
igendel

Xiao RP2040 MicroPython Membrane Keypad PIN Reader

Nov 6th, 2022
944
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Python 3.00 KB | None | 0 0
  1. # Xiao RP2040 Membrane keypad "PIN code" reader
  2. # by Ido Gendel, 2022
  3. # Connections:
  4. #   D7 (P1) -> 510R -> Buzzer -> GND
  5. #   D10 (P3) -> Red LED [Cathode] -> 510R -> 3V3
  6. #   D10 (p3) -> Green LED [Anode] -> 510R -> GND
  7. #   D0-2 (p26-28) -> Keypad columns
  8. #   D3-6 (p29,6,7,0) -> Keypad rows
  9.  
  10.  
  11. from machine import Pin, PWM, Timer
  12. import time
  13.  
  14. # Constants
  15. #================================
  16.  
  17. # This is a demo, not a secure application!
  18. SECRET_CODE = const("4567*")
  19.  
  20. KEYPAD_TIMEOUT = const(5000)
  21. BEEP_FREQ = const(360)
  22.  
  23. row_pin_ref = (0,7,6,29)
  24. # For each column in the keypad, pin ref and keys
  25. key_map = ((28, ("1", "4", "7", "*")),
  26.            (27, ("2", "5", "8", "0")),
  27.            (26, ("3", "6", "9", "#")))
  28.  
  29.  
  30. # Functions
  31. #================================
  32.  
  33. def read_keypad(caller):
  34.    
  35.     global col_pin, row_pin
  36.     global keypad_input
  37.     global last_key
  38.     global last_key_time, KEYPAD_TIMEOUT
  39.     global beep_flag
  40.    
  41.     # Scan for keypad short circuit and get appropriate key value
  42.     result = ""
  43.     for col in range(len(col_pin)):
  44.         if result == "":
  45.             col_pin[col].init(Pin.OUT)
  46.             col_pin[col].low()
  47.             for row in range(len(row_pin)):
  48.                 if row_pin[row].value() == 0:
  49.                     result = key_map[col][1][row]
  50.                     beep_flag = True
  51.                     break
  52.             col_pin[col].init(Pin.IN)
  53.  
  54.     # Avoid artificial repetitions
  55.     if result != last_key:
  56.         # Reset iput string if timed out
  57.         if time.ticks_diff(time.ticks_ms(), last_key_time) > KEYPAD_TIMEOUT:
  58.             keypad_input = ""
  59.         last_key_time = time.ticks_ms()
  60.         last_key = result
  61.         keypad_input += result
  62.  
  63.  
  64. # Global variables and setup
  65. #================================
  66.  
  67. row_pin = []
  68. for pin_ref in row_pin_ref:
  69.     row_pin.append(Pin(pin_ref, Pin.IN, pull=Pin.PULL_UP))
  70.    
  71. col_pin = []
  72. for key in key_map:
  73.     col_pin.append(Pin(key[0], Pin.IN))
  74.  
  75. keypad_input = ""
  76. last_key = "Unlikely!"
  77. last_key_time = time.ticks_ms()
  78. beep_flag = False
  79.  
  80. keypad_timer = Timer(-1, mode=Timer.PERIODIC, period=50,
  81.                      callback=read_keypad)
  82.  
  83. led_pin = Pin(3, Pin.OUT)
  84. led_pin.low()
  85. led_timer = Timer(-1)
  86.  
  87. buzzer_pin = Pin(1)
  88. buzzer_pwm = PWM(buzzer_pin)
  89. buzzer_pwm.deinit()
  90. buzzer_timer = Timer(-1)
  91.  
  92.  
  93. # Main loop
  94. #================================
  95.  
  96. while True:
  97.  
  98.     if keypad_input.find(SECRET_CODE) >= 0:
  99.         led_pin.high()
  100.         led_timer.init(mode=Timer.ONE_SHOT, period=2500,
  101.                        callback=lambda caller:led_pin.low())
  102.         keypad_input = ""
  103.  
  104.     # Prevent memory overflow, without losing last presses
  105.     elif len(keypad_input) > 32:
  106.         keypad_input = keypad_input[16:]
  107.    
  108.     if beep_flag:
  109.         buzzer_pwm.freq(BEEP_FREQ)
  110.         buzzer_pwm.duty_u16(32768)
  111.         buzzer_timer.init(mode=Timer.ONE_SHOT, period=60,
  112.                           callback=lambda caller:buzzer_pwm.deinit())        
  113.         beep_flag = False
  114.    
  115.    
  116.  
  117.  
  118.  
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement