2012-12-26 4 views
0

플레이어로부터 입력을 얻기 위해 게임 프로세스를 중단하지 않고 플레이어가 WASD 키를 누르라는 스네이크 게임을 만들고 있습니다. 그래서 나는이 상황을 위해 input()을 사용할 수 없습니다. 게임이 입력을 얻기 위해 똑딱 거리지 않기 때문입니다.스레드를 사용하여 파이썬 3에서 키보드 입력을 얻는 방법?

Enter를 누르지 않고 즉시 입력을 제공하는기능을 찾았지만 input()과 같은 입력을 얻으려면 게임 감추기도 중지하십시오. 다른 스레드에서 getch()을 통해 입력을 얻으려면 스레딩 모듈을 사용하기로 결정했습니다. 문제는 다른 스레드에서 getch()가 작동하지 않고 이유가 확실하지 않다는 것입니다. thread1()에이를 때

import threading, time 
from msvcrt import getch 

key = "lol" #it never changes because getch() in thread1 is useless 

def thread1(): 
    while True: 
     key = getch() #this simply is almost ignored by interpreter, the only thing it 
     #gives is that delays print() unless you press any key 
     print("this is thread1()") 

threading.Thread(target = thread1).start() 

while True: 
    time.sleep(1) 
    print(key) 

는 왜 getch() 쓸모가?

+0

. 그것은 키보드에서 눌려지고있는 키를 쉽게 알 수 있도록 해주는 함수를 가지고있어서 쓰레드로 돌아 다닐 필요가 없습니다. – Michael0x2a

답변

5

기존 로컬 변수를 덮어 쓰는 대신 로컬 변수 keythread1 안에 생성하는 것이 문제였습니다. 빠르고 손쉬운 해결책은 keythread1 안에 전역으로 선언하는 것입니다.

마지막으로 잠금 사용을 고려해야합니다. 나는 그것이 필요한지 아닌지는 모르지만, 같은 시간에 인쇄 할 때 스레드에서 key 값을 쓰고 쓰면 이상한 일이 발생할 수 있다고 상상합니다.

작업 코드 : 당신은 설치 및 파이 게임을 사용하는 대신 스레드를 사용하는 것이 좋습니다

import threading, time 
from msvcrt import getch 

key = "lol" 

def thread1(): 
    global key 
    lock = threading.Lock() 
    while True: 
     with lock: 
      key = getch() 

threading.Thread(target = thread1).start() 

while True: 
    time.sleep(1) 
    print(key) 
+0

thread1()이 말한 것처럼 반복되지 않기 때문에 작동하지 않습니다. "true :"thread1()의 모든 것이 완벽하게 작동하기 시작했습니다. 그리고 스레딩이 뭔지도 모릅니다 .Lock() – foxneSs

+0

@foxneSs : 아, 당신은 '사실이지만.'- 내 잘못이야. 나는 내 대답을 편집했다. 'threading.Lock'은 잠금이 활성화되어있을 때 스레드 만이 'key'변수를 수정할 수 있도록합니다. 추가 정보 : http://stackoverflow.com/questions/6393073/why-should-you-lock-threads – Michael0x2a

0

getch를 사용해 보았지만 나에게 적합하지 않았습니다 ... (win7 여기).

당신은 Tkinter의 모듈을 사용하여 시도 할 수 있습니다 //하지만, 난 여전히 Michael0x2a 당신이 게임을 만들기 위해 만든 라이브러리를 사용하려고 할 수 있습니다 말했듯이 스레드

# Respond to a key without the need to press enter 
import tkinter as tk #on python 2.x use "import Tkinter as tk" 

def keypress(event): 
    if event.keysym == 'Escape': 
     root.destroy() 
    x = event.char 
    if x == "w": 
     print ("W pressed") 
    elif x == "a": 
     print ("A pressed") 
    elif x == "s": 
     print ("S pressed") 
    elif x == "d": 
     print ("D pressed") 
    else: 
     print (x) 

root = tk.Tk() 
print ("Press a key (Escape key to exit):") 
root.bind_all('<Key>', keypress) 
# don't show the tk window 
root.withdraw() 
root.mainloop() 

실행 할 수 없습니다 - 파이 게임 또는 pyglet을.

@ EDIT @ Michael0x2a : 코드가 작동합니까? 내가 무엇을 눌러도 항상 동일한 키가 인쇄됩니다.

@ EDIT2 : 고마워요!

+1

어떤 이유로 든 getch는 명령 행에서만 작동하는 것으로 보입니다. 유휴 상태에서 파일을 실행하면 작동하지 않는 것 같습니다. – Michael0x2a

관련 문제