123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219 |
- #!/usr/bin/env python3
- # -*- coding: utf-8 -*-
- import subprocess
- import select
- import signal
- import time
- import sys
- import os
- from PIL import Image
- from PIL import ImageDraw
- from PIL import ImageFont
- import ST7735 as TFT
- import Adafruit_GPIO.SPI as SPI
- import RPi.GPIO as GPIO
- # LCD spec.
- LCD_WIDTH = 128
- LCD_HEIGHT = 160
- SPEED_HZ = 8000000
- # SUPERDAC configration
- DC = 24
- RST = 23
- SPI_PORT = 0
- SPI_DEVICE = 0
- SW1 = 5
- SW2 = 6
- FONTSIZE=14
- LINEHEIGHT=16
- DEFAULT_FONT = '/usr/share/fonts/truetype/fonts-japanese-gothic.ttf'
- IR_CONF='/etc/lirc/lircd.conf.d/remocon.lircd.conf'
- MODE2CMD=['/usr/bin/mode2', '--device', '/dev/lirc0', '--driver','default']
- BUTTONS=[ {'label': 'PLAY', 'prompt': 'プレイ', 'code': None},\
- {'label': 'STOP', 'prompt': 'ストップ', 'code': None},\
- {'label': 'PAUSE', 'prompt': '一時停止', 'code': None},\
- {'label': 'NEXT', 'prompt': '次曲', 'code': None},\
- {'label': 'PREV', 'prompt': '前曲', 'code': None},\
- {'label': 'VOLUP', 'prompt': '音量上げ', 'code': None},\
- {'label': 'VOLDOWN', 'prompt': '音量下げ', 'code': None},\
- {'label': 'MENU', 'prompt': 'メニュー', 'code': None},\
- {'label': '0', 'prompt': '数字0', 'code': None},\
- {'label': '1', 'prompt': '数字1', 'code': None},\
- {'label': '2', 'prompt': '数字2', 'code': None},\
- {'label': '3', 'prompt': '数字3', 'code': None},\
- {'label': '4', 'prompt': '数字4', 'code': None},\
- {'label': '5', 'prompt': '数字5', 'code': None},\
- {'label': '6', 'prompt': '数字6', 'code': None},\
- {'label': '7', 'prompt': '数字7', 'code': None},\
- {'label': '8', 'prompt': '数字8', 'code': None},\
- {'label': '9', 'prompt': '数字9', 'code': None},\
- ]
- STR_GUIDE=['リモコンの登録を',\
- '行います。',\
- 'リモコンの任意の',\
- 'ボタンを5分以内',\
- 'に押してください。',\
- '信号を検出し',\
- '登録を開始します。',\
- ]
- STR_MESSAGE=['ボタンを',\
- '押してください。',\
- '(2分以内)',
- ]
- STR_ERR = ['タイムアウト',\
- 'リモコンの信号が',\
- '受信できません',\
- ]
-
- STR_END = ['登録完了です',\
- '自動的に再起動',\
- 'します。',\
- '再起動後リモコン',\
- 'が使えるかテスト',\
- 'してください',\
- 'SW1でいつでも',\
- '再登録できます',\
- ]
- LCD = None
- class simpleLCD():
-
- def __init__(self):
- spi = SPI.SpiDev(SPI_PORT, SPI_DEVICE,max_speed_hz=SPEED_HZ)
- self.disp = TFT.ST7735(DC, rst=RST, spi=spi)
- self.disp.begin()
- self.disp.clear((0,0,0));
- self.disp.display()
- self.draw=ImageDraw.Draw(self.disp.buffer)
- self.font = ImageFont.truetype(DEFAULT_FONT, FONTSIZE, encoding="unic");
- self.clear()
-
- def clear(self):
- self.disp.clear((0,0,0))
-
- def message(self, msg, y = 0, c = '#FFFFFF'):
- for line in msg:
- self.draw.text((0, y), line, font=self.font, fill=c)
- y += LINEHEIGHT
- self.disp.display()
- return y
- def receiveIr(timeout=120*1000):
- codes = []
- with subprocess.Popen(MODE2CMD, stdout=subprocess.PIPE, stderr=subprocess.DEVNULL) as proc:
- p = select.poll()
- p.register(proc.stdout)
- i = 0
- fstart = False
- while True:
- ret = p.poll(timeout)
- if len(ret) == 0: # timeout
- proc.terminate()
- return None
- line = proc.stdout.readline().strip().decode()
- type = line.split(' ')[0]
- code = line.split(' ')[1]
- if not fstart:
- if type == 'pulse':
- fstart = True
-
- if fstart:
- codes.append(code)
- i += 1
-
- if i >= 67:
- break
-
- proc.terminate()
- return codes
- def timeout():
- global LCD
-
- LCD.clear()
- LCD.message(STR_ERR, c='#FF0000')
- time.sleep(60)
- os.system('/sbin/reboot')
- sys.exit(1)
- #
- # Script starts here
- if __name__ == "__main__":
- # switch
- GPIO.setmode(GPIO.BCM)
- GPIO.setup(SW1, GPIO.IN, pull_up_down=GPIO.PUD_UP)
- sw = GPIO.input(SW1)
- GPIO.cleanup()
- if sw != GPIO.LOW:
- sys.exit(0)
-
- # stop service
- # move /sbin -> /bin ...
- os.system('systemctl stop lircd')
- os.system('systemctl stop superdac')
- os.system('systemctl stop mpd')
- time.sleep(20)
- #
- LCD = simpleLCD()
- LCD.message(STR_GUIDE)
- r = receiveIr(5*60*1000)
- if r is None:
- timeout()
-
- # Learn
- for item in BUTTONS:
- LCD.clear()
- y = LCD.message( [item['prompt']], c='#FF0000')
- LCD.message(STR_MESSAGE, y=y)
- r = receiveIr(2*60*1000)
- if r is None:
- timeout()
- item['code'] = r
-
- # config
- # print(BUTTONS)
- with open(IR_CONF, 'w') as f:
- print('begin remote' , file=f)
- print('' , file=f)
- print(' name remocon' , file=f)
- print(' flags RAW_CODES|CONST_LENGTH' , file=f)
- print(' eps 30' , file=f)
- print(' aeps 100' , file=f)
- print(' gap 100000' , file=f)
- print('' , file=f)
- print(' begin raw_codes' , file=f)
- for item in BUTTONS:
- code = item['code']
- print(' name ' + item['label'], file=f)
- for i in range(12):
- f.write(' ')
- for j in range(6):
- try:
- c = code.pop(0)
- f.write(c.rjust(8))
- except Exception as e:
- break
- f.write('\n')
- print(' end raw_codes' , file=f)
- print('end remote' , file=f)
- LCD.clear()
- LCD.message(STR_END)
- time.sleep(30)
- os.system('/sbin/reboot')
- sys.exit(0)
|