Un Macropad programabil cu scopul de a eficientiza lucrul pe calculator. Am plecat de la dorinta de a controla mai eficient functionalitati ale laptopului meu in timp ce lucrez precum:
Acest proiect este util pentru minimizarea timpului mort
Lista componente:
Codul a fost dezvoltat folosind limbajul CircuitPython in Thonny. Biblioteci externe:
Codul citeste semnale de la cele 10 butoane si de la codorul rotativ, inclusiv butonul acestuia
Pentru a programa functionalitatea celor 10 butoane, trebuie definita o matrice de 5×2 cu functionalitatea pentru foecare butoane. Functionalitatea butoanelor este preluata din biblioteca Adafruit HID.
Pentru controlul OLED-ului se foloseste biblioteca Adafruit SSD1306 si Adafruit ImageLoader. Se pot scrie mesaje caracter cu caracter, se pot incarca imagini sau se pot seta pixeli arbitrar pe o matrice de 128×64 pixeli.
import rotaryio import board import digitalio import displayio import adafruit_imageload import usb_hid from adafruit_hid.consumer_control import ConsumerControl from adafruit_hid.consumer_control_code import ConsumerControlCode import time from digitalio import DigitalInOut, Direction, Pull from adafruit_hid.keyboard import Keyboard from adafruit_hid.keycode import Keycode import busio import adafruit_ssd1306 #display i2c = busio.I2C(board.GP27, board.GP26) display = adafruit_ssd1306.SSD1306_I2C(128, 64, i2c) # left encoder buttonL = digitalio.DigitalInOut(board.GP6) buttonL.direction = digitalio.Direction.INPUT buttonL.pull = digitalio.Pull.UP encoderL = rotaryio.IncrementalEncoder(board.GP7, board.GP8) cc = ConsumerControl(usb_hid.devices) button_stateL = None last_positionL = encoderL.position # keyboard led = DigitalInOut(board.LED) led.direction = Direction.OUTPUT led.value = True kbd = Keyboard(usb_hid.devices) cck = ConsumerControl(usb_hid.devices) pins = [ board.GP13, board.GP12, board.GP11, board.GP10, board.GP16, board.GP17, board.GP18, board.GP19, board.GP20, board.GP21, ] MEDIA = 1 KEY = 2 META = 3 # functionality of each layer keymap_layers = [{ (0): (KEY, [Keycode.ONE]), (1): (KEY, [Keycode.TWO]), (2): (KEY, [Keycode.THREE]), (3): (KEY, [Keycode.FOUR]), (4): (META, [Keycode.CAPS_LOCK]), (5): (KEY, (Keycode.SHIFT, Keycode.GUI, Keycode.M)), (6): (KEY, [Keycode.FIVE]), (7): (KEY, [Keycode.SIX]), (8): (KEY, [Keycode.SEVEN]), (9): (KEY, [Keycode.EIGHT]), }, { (0): (KEY, [Keycode.NINE]), (1): (KEY, [Keycode.ZERO]), (2): (KEY, (Keycode.SHIFT, Keycode.NINE)), (3): (KEY, (Keycode.SHIFT, Keycode.ZERO)), (4): (META, [Keycode.CAPS_LOCK]), (5): (KEY, (Keycode.SHIFT, Keycode.GUI, Keycode.M)), (6): (KEY, (Keycode.SHIFT, Keycode.THREE)), (7): (KEY, (Keycode.SHIFT, Keycode.FOUR)), (8): (KEY, (Keycode.SHIFT, Keycode.SEVEN)), (9): (KEY, (Keycode.SHIFT, Keycode.EIGHT)), }] keymap = keymap_layers[0] layer = True mute = False # display layers based on keyboard layer def change_layer(mute): global keymap if layer: display.fill(0) keymap = keymap_layers[not layer] display.text("layer 1 2 3 4", 0, 0, 1) if mute == True: display.text("unmute 5 6 7 8", 0, 32, 1) else: display.text("mute 5 6 7 8", 0, 32, 1) display.show() else: display.fill(0) keymap = keymap_layers[not layer] display.text("layer 9 0 ( )", 0, 0, 1) if mute == True: display.text("unmute # $ & *", 0, 32, 1) else: display.text("mute # $ & *", 0, 32, 1) display.show() switches = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9] for i in range(10): switches[i] = DigitalInOut(pins[i]) switches[i].direction = Direction.INPUT switches[i].pull = Pull.UP switch_state = [0, 0, 0, 0, 0, 0, 0, 0, 0, 0] # init change_layer(mute) while True: # left encoder current_positionL = encoderL.position position_changeL = current_positionL - last_positionL if position_changeL > 0: for _ in range(position_changeL): cc.send(ConsumerControlCode.VOLUME_DECREMENT) #print(current_positionL) elif position_changeL < 0: for _ in range(-position_changeL): cc.send(ConsumerControlCode.VOLUME_INCREMENT) #print(current_positionL) last_positionL = current_positionL if not buttonL.value and button_stateL is None: button_stateL = "pressed" if buttonL.value and button_stateL == "pressed": cc.send(ConsumerControlCode.MUTE) button_stateL = None # keyboard for button in range(10): if switch_state[button] == 0: if not switches[button].value: try: if keymap[button][0] == KEY: if button == 5: mute = not mute change_layer(mute) kbd.press(*keymap[button][1]) else: if button == 4: layer = not layer change_layer(mute) else: cck.send(keymap[button][1]) except ValueError: # deals w six key limit pass switch_state[button] = 1 if switch_state[button] == 1: if switches[button].value: try: if keymap[button][0] == KEY: kbd.release(*keymap[button][1]) except ValueError: pass switch_state[button] = 0 time.sleep(0.01) # debounce
Am dobandit skill-ul de a face un PCB de mana. Am produs un tool pe care il voi folosi in timpul lucrului de zi cu zi
Rezultatul proiectului este un punct bun de inceput prototiparea unui produs care poate fi adus pe piata
Resurse Software
Resurse Hardware.