본문 바로가기
Programming/Python_Etc

Python 키보드로 소리내기 피아노 연주하기

by Wilkyway 2021. 10. 13.
반응형

키보드 입력에 맞추어 비프음을 내도록 하겠습니다. 이번 프로그램을 위해서는 비프음을 내도록 하는 windsound 모듈과 키보드 인풋을 받아들이는 pynput 모듈이 필요합니다. 그 중 windwound 모듈은 기본으로 내장되어있으니 pynput 모듈만 설치해주도록 합니다.

 

1. 라이브러리 설치

pip install pynput

 

2. pynput모듈

pynput 모듈에서는 on_press 이벤트와 on_release 이벤트에 대해 리스너를 통해 입력받는 방법이 있습니다.

from pynput import keyboard

def on_press(key):
    print('Pressed Key: %s' % key)

def on_release(key):
    print('Pressed Key: %s' % key)
    if key == keyboard.Key.esc: #esc 키가 입력되면 종료
        return False
        
 # 리스너 등록방법1
listener = keyboard.Listener(
     on_press=on_press,
     on_release=on_release)
listener.start()
listener.join()

# 리스너 등록방법2
with keyboard.Listener(
    on_press=on_press,
    on_release=on_release) as listener:
    listener.join()

이런식으로 이용하면 되지만, 이번에는 동기화 방식에 의한 방법으로

from pynput import keyboard
 
with keyboard.Events() as events:
    for event in events:
        if event.key == keyboard.Key.esc:
            print("Exit!!")
            break
        if event.key == keyboard.KeyCode(char='a'):
            print("Pressed:", keyboard.KeyCode(char='a'))

와 같이 사용하려고 합니다. 이벤트의 종류와 상관없이 처리를 하게 됩니다.

 

3. winsound 모듈

winsound.Beep(음계주파수, 지속시간)

와 같이 사용합니다. 연주를 위해서는 음계에 대한 정확한 주파수를 입력해야합니다. 다행스러운 것은 한 옥타브 위의 음에 대해서는 2배의 Frequency에 해당하는 주파수를 갖고 있습니다.

 

4. 전체 소스코드

from pynput import keyboard
import winsound

# 1옥타브: C, C#, D, D#, E, F, F#, G, G#, A, A#, B
pitch = {'c_': 523, 'cs': 554, 'd_': 587, 'ds': 622, 'e_': 659,
         'f_': 698, 'fs': 740, 'g_': 784, 'gs': 831, 'a_': 880,
         'as': 932, 'b_': 988}
# 2옥타브
pitch2={}
for key, value in pitch.items():
    pitch2[key] = value * 2  # 한옥타브 위는 주파수가 2배.
print(pitch2)

# 지속시간
lasting = 100

# The event listener will be running in this block
with keyboard.Events() as events:
    for event in events:
        if event.key == keyboard.Key.esc:
            print("Exit!!")
            break
        elif event.key == keyboard.KeyCode(char='q'):
            winsound.Beep(494, lasting)
        elif event.key == keyboard.KeyCode(char='a'):
            winsound.Beep(pitch['c_'], lasting)
        elif event.key == keyboard.KeyCode(char='w'):
            winsound.Beep(pitch['cs'], lasting)
        elif event.key == keyboard.KeyCode(char='s'):
            winsound.Beep(pitch['d_'], lasting)
        elif event.key == keyboard.KeyCode(char='e'):
            winsound.Beep(pitch['ds'], lasting)
        elif (event.key == keyboard.KeyCode(char='d')) | (event.key == keyboard.KeyCode(char='r')):
            winsound.Beep(pitch['e_'], lasting)
        elif event.key == keyboard.KeyCode(char='f'):
            winsound.Beep(pitch['f_'], lasting)
        elif event.key == keyboard.KeyCode(char='t'):
            winsound.Beep(pitch['fs'], lasting)
        elif event.key == keyboard.KeyCode(char='g'):
            winsound.Beep(pitch['g_'], lasting)
        elif event.key == keyboard.KeyCode(char='y'):
            winsound.Beep(pitch['gs'], lasting)
        elif event.key == keyboard.KeyCode(char='h'):
            winsound.Beep(pitch['a_'], lasting)
        elif event.key == keyboard.KeyCode(char='u'):
            winsound.Beep(pitch['as'], lasting)
        elif (event.key == keyboard.KeyCode(char='j')) | (event.key == keyboard.KeyCode(char='i')):
            winsound.Beep(pitch['b_'], lasting)
        elif event.key == keyboard.KeyCode(char='k'):
            winsound.Beep(pitch2['c_'], lasting)
        elif event.key == keyboard.KeyCode(char='o'):
            winsound.Beep(pitch2['cs'], lasting)
        elif event.key == keyboard.KeyCode(char='l'):
            winsound.Beep(pitch2['d_'], lasting)
        elif event.key == keyboard.KeyCode(char='p'):
            winsound.Beep(pitch2['ds'], lasting)
        elif (event.key == keyboard.KeyCode(char=';')) | (event.key == keyboard.KeyCode(char='[')):
            winsound.Beep(pitch2['e_'], lasting)
        elif event.key == keyboard.KeyCode(char="'"):
            winsound.Beep(pitch2['f_'], lasting)
        elif event.key == keyboard.KeyCode(char="]"):
            winsound.Beep(pitch2['fs'], lasting)

# 빈 키(z,x,c,v... ) 에 대해 추가로 음계 할당
        elif event.key == keyboard.KeyCode(char="z"):
            winsound.Beep(pitch['c_'], lasting)
        elif event.key == keyboard.KeyCode(char="x"):
            winsound.Beep(pitch['d_'], lasting)
        elif event.key == keyboard.KeyCode(char="c"):
            winsound.Beep(pitch['e_'], lasting)
        elif event.key == keyboard.KeyCode(char="v"):
            winsound.Beep(pitch['f_'], lasting)
        elif event.key == keyboard.KeyCode(char="b"):
            winsound.Beep(pitch['g_'], lasting)
        elif event.key == keyboard.KeyCode(char="n"):
            winsound.Beep(pitch['a_'], lasting)
        elif event.key == keyboard.KeyCode(char="m"):
            winsound.Beep(pitch['b_'], lasting)
        elif event.key == keyboard.KeyCode(char=","):
            winsound.Beep(pitch2['c_'], lasting)
        elif event.key == keyboard.KeyCode(char="."):
            winsound.Beep(pitch2['d_'], lasting)
        elif event.key == keyboard.KeyCode(char="/"):
            winsound.Beep(pitch2['e_'], lasting)

 

이상으로 연주 가능한 키보드를 만들어보았습니다.

 

~~끝~~

반응형

댓글