दिलचस्प पोस्ट
JSON प्रारूप में पोस्ट डेटा पायथन इंटरैक्टिव सत्र को कैसे सहेजना है? एंड्रॉइड स्टूडियो में बाह्य पुस्तकालय जोड़ना 'फॉर्म ग्रुप' से बाध्य नहीं किया जा सकता क्योंकि यह 'प्रपत्र' की ज्ञात संपत्ति नहीं है देशी वस्तुओं को एक बुरा अभ्यास क्यों बढ़ा रहा है? इनपुट प्रकार = "फ़ाइल" पर कर्सर प्रकार बदलें V38 के बाद से, क्रोम एक्सटेंशन अब HTTP यूआरएल से लोड नहीं कर सकता, वैकल्पिक हल? गेरिट और हडसन के लिए एसएसएच कुंजी बनाना Sass में एक नंबर को एक इकाई जोड़ना सिम्युलेटर में स्विफ्ट (आईओएस 8) में एमएफमेल कॉम्पोज़ वीक कंट्रोलर के साथ असली गलतफहमी है URL खंड और 302 रीडायरेक्ट्स एंड्रॉइड में मार्की टेक्स्ट एएसपी.NET एमवीसी में आधार नियंत्रक वर्ग के लिए अच्छे उम्मीदवार कौन हैं? वक्रार (अधिकतम) हर जगह? CSS का उपयोग करते हुए वैकल्पिक तालिका पंक्ति का रंग?

पायथन उपयोगकर्ता से एक अक्षर पढ़ता है

क्या उपयोगकर्ता इनपुट से एक एकल वर्ण को पढ़ने का एक तरीका है? उदाहरण के लिए, वे टर्मिनल पर एक कुंजी दबाते हैं और इसे लौटा दिया जाता है (जैसे कि getch() की तरह) मुझे पता है कि इसके लिए विंडोज में एक फ़ंक्शन है, लेकिन मुझे कुछ ऐसा चाहिए जो क्रॉस-प्लेटफॉर्म है

वेब के समाधान से एकत्रित समाधान "पायथन उपयोगकर्ता से एक अक्षर पढ़ता है"

यहां एक साइट के लिए एक लिंक है जो कहता है कि आप विंडोज, लिनक्स और ओएसएक्स में एक अक्षर कैसे पढ़ सकते हैं: http://code.activestate.com/recipes/134892/

 class _Getch: """Gets a single character from standard input. Does not echo to the screen.""" def __init__(self): try: self.impl = _GetchWindows() except ImportError: self.impl = _GetchUnix() def __call__(self): return self.impl() class _GetchUnix: def __init__(self): import tty, sys def __call__(self): import sys, tty, termios fd = sys.stdin.fileno() old_settings = termios.tcgetattr(fd) try: tty.setraw(sys.stdin.fileno()) ch = sys.stdin.read(1) finally: termios.tcsetattr(fd, termios.TCSADRAIN, old_settings) return ch class _GetchWindows: def __init__(self): import msvcrt def __call__(self): import msvcrt return msvcrt.getch() getch = _Getch() 
 sys.stdin.read(1) 

मूल रूप से 1 बाइट एसटीडीआईएन से पढ़ा जाएगा

यदि आपको उस विधि का उपयोग करना चाहिए जो कि प्रतीक्षा नहीं करता है \n आप इस कोड का उपयोग पिछले उत्तर में सुझाए अनुसार कर सकते हैं:

 class _Getch: """Gets a single character from standard input. Does not echo to the screen.""" def __init__(self): try: self.impl = _GetchWindows() except ImportError: self.impl = _GetchUnix() def __call__(self): return self.impl() class _GetchUnix: def __init__(self): import tty, sys def __call__(self): import sys, tty, termios fd = sys.stdin.fileno() old_settings = termios.tcgetattr(fd) try: tty.setraw(sys.stdin.fileno()) ch = sys.stdin.read(1) finally: termios.tcsetattr(fd, termios.TCSADRAIN, old_settings) return ch class _GetchWindows: def __init__(self): import msvcrt def __call__(self): import msvcrt return msvcrt.getch() getch = _Getch() 

( http://code.activestate.com/recipes/134892/ से लिया गया )

एक्टिवेटेट नुस्खा ने दो जवाबों में शब्दशः उद्धृत किया है, जो अति-इंजीनियर है। इसे नीचे उबला जा सकता है:

 def _find_getch(): try: import termios except ImportError: # Non-POSIX. Return msvcrt's (Windows') getch. import msvcrt return msvcrt.getch # POSIX system. Create and return a getch that manipulates the tty. import sys, tty def _getch(): fd = sys.stdin.fileno() old_settings = termios.tcgetattr(fd) try: tty.setraw(fd) ch = sys.stdin.read(1) finally: termios.tcsetattr(fd, termios.TCSADRAIN, old_settings) return ch return _getch getch = _find_getch() 

कोशिश करने के लायक भी प्रकाशक है, जो कि अन्य उत्तर में उल्लेखित ActiveState नुस्खा पर आधारित है।

स्थापना:

 pip install readchar 

उपयोग:

 import readchar print("Reading a char:") print(repr(readchar.readchar())) print("Reading a key:") print(repr(readchar.readkey())) 

पायथन 2.7 के साथ विंडोज और लिनक्स पर परीक्षण

विंडोज़ में, केवल चाबी जो अक्षरों या एएससीआईआई नियंत्रण कोड को मैप करते हैं ( बैकस्पेस , एन्टर , एस्क , टैब , Ctrl + पत्र ) समर्थित हैं। जीएनयू / लिनक्स पर (सटीक टर्मिनल के आधार पर, शायद?) आप भी सम्मिलित करें , हटाएं , पीजी अप , पीजी डीएन , होम , एंड और एफ एन कुंजी प्राप्त कर सकते हैं … लेकिन फिर, इन विशेष कुंजी को एक Esc से अलग करने के मुद्दे हैं

चेतावनी: यहां पर अधिकांश (सभी?) उत्तरों की तरह, Ctrl + C , Ctrl + D और Ctrl + Z जैसे संकेत कुंजी पकड़े गए और वापस ( '\x03' , '\x04' और '\x1a' ); आपके कार्यक्रम को रोकना मुश्किल हो सकता है

एक वैकल्पिक तरीका:

 import os import sys import termios import fcntl def getch(): fd = sys.stdin.fileno() oldterm = termios.tcgetattr(fd) newattr = termios.tcgetattr(fd) newattr[3] = newattr[3] & ~termios.ICANON & ~termios.ECHO termios.tcsetattr(fd, termios.TCSANOW, newattr) oldflags = fcntl.fcntl(fd, fcntl.F_GETFL) fcntl.fcntl(fd, fcntl.F_SETFL, oldflags | os.O_NONBLOCK) try: while 1: try: c = sys.stdin.read(1) break except IOError: pass finally: termios.tcsetattr(fd, termios.TCSAFLUSH, oldterm) fcntl.fcntl(fd, fcntl.F_SETFL, oldflags) return c 

इस ब्लॉग पोस्ट से

मुझे लगता है कि इस बिंदु पर यह बेहद मुश्किल हो जाता है, और विभिन्न प्लेटफार्मों पर डिबगिंग एक बड़ा गड़बड़ है

यदि आप कुछ इस तरह से अधिक विस्तृत कर रहे हैं और दृश्यों की आवश्यकता होगी, या यदि आप टर्मिनल के साथ काम करने जा रहे हैं तो पेगलेट, पैगमेम, कोकोज -2 डी जैसे कुछ का उपयोग करना बेहतर होगा।

कर्ज़ मानक है: http://docs.python.org/library/curses.html

यह कोड, यहां पर आधारित है, सही ढंग से कुंजीपटल इंटरर्यूट और EOFError बढ़ाएगा अगर Ctrl + C या Ctrl + D दबाया जाता है।

विंडोज और लिनक्स पर काम करना चाहिए। एक ओएस एक्स संस्करण मूल स्रोत से उपलब्ध है।

 class _Getch: """Gets a single character from standard input. Does not echo to the screen.""" def __init__(self): try: self.impl = _GetchWindows() except ImportError: self.impl = _GetchUnix() def __call__(self): char = self.impl() if char == '\x03': raise KeyboardInterrupt elif char == '\x04': raise EOFError return char class _GetchUnix: def __init__(self): import tty import sys def __call__(self): import sys import tty import termios fd = sys.stdin.fileno() old_settings = termios.tcgetattr(fd) try: tty.setraw(sys.stdin.fileno()) ch = sys.stdin.read(1) finally: termios.tcsetattr(fd, termios.TCSADRAIN, old_settings) return ch class _GetchWindows: def __init__(self): import msvcrt def __call__(self): import msvcrt return msvcrt.getch() getch = _Getch() 

(वर्तमान में) शीर्ष-क्रमित उत्तर (एक्टिवेटेट कोड के साथ) अति जटिल है जब वर्गों का उपयोग करने के लिए पर्याप्त कार्य होना चाहिए तो मुझे कक्षाओं का उपयोग करने का कोई कारण नहीं दिख रहा है नीचे दो कार्यान्वयन हैं जो एक ही चीज़ को पूरा करते हैं लेकिन अधिक पठनीय कोड के साथ।

इन दोनों कार्यान्वयन:

  1. पायथन 2 या पायथन 3 में ठीक काम करें
  2. विंडोज, ओएसएक्स, और लिनक्स पर काम करें
  3. सिर्फ एक बाइट पढ़ें (यानी, वे एक नई लाइन के लिए प्रतीक्षा नहीं करते हैं)
  4. किसी भी बाहरी पुस्तकालयों पर निर्भर न करें
  5. आत्म निहित हैं (फ़ंक्शन परिभाषा के बाहर कोई कोड नहीं)

संस्करण 1: पठनीय और सरल

 def getChar(): try: # for Windows-based systems import msvcrt # If successful, we are on Windows return msvcrt.getch() except ImportError: # for POSIX-based systems (with termios & tty support) import tty, sys, termios # raises ImportError if unsupported fd = sys.stdin.fileno() oldSettings = termios.tcgetattr(fd) try: tty.setcbreak(fd) answer = sys.stdin.read(1) finally: termios.tcsetattr(fd, termios.TCSADRAIN, oldSettings) return answer 

संस्करण 2: बार-बार आयात और अपवाद से निपटने से बचें:

[संपादित करें] मैंने ActiveState कोड का एक फायदा खो दिया है। यदि आप कई बार अक्षरों को पढ़ने की योजना बना रहे हैं, तो यह कोड विंडोज आयात को दोहराते हुए (यूनिवर्सल) लागत को रद्द कर देता है और यूनिक्स जैसी प्रणालियों पर इंपोर्ट इर्रर अपवाद हैंडलिंग जब आपको संभवतः उस नगण्य ऑप्टिमाइजेशन की तुलना में कोड पठनीयता के बारे में अधिक चिंतित होना चाहिए, तो यह एक विकल्प है (यह लुईस के उत्तर के समान है, लेकिन getChar () आत्म-निहित है) जो कि सक्रियस्टेट कोड के समान कार्य करता है और अधिक पठनीय है:

 def getChar(): # figure out which function to use once, and store it in _func if "_func" not in getChar.__dict__: try: # for Windows-based systems import msvcrt # If successful, we are on Windows getChar._func=msvcrt.getch except ImportError: # for POSIX-based systems (with termios & tty support) import tty, sys, termios # raises ImportError if unsupported def _ttyRead(): fd = sys.stdin.fileno() oldSettings = termios.tcgetattr(fd) try: tty.setcbreak(fd) answer = sys.stdin.read(1) finally: termios.tcsetattr(fd, termios.TCSADRAIN, oldSettings) return answer getChar._func=_ttyRead return getChar._func() 

उदाहरण कोड जो ऊपर के getChar () संस्करणों में से एक का उपयोग करता है:

 from __future__ import print_function # put at top of file if using Python 2 # Example of a prompt for one character of input promptStr = "Please give me a character:" responseStr = "Thank you for giving me a '{}'." print(promptStr, end="\n> ") answer = getChar() print("\n") print(responseStr.format(answer)) 

यह संदर्भ मैनेजर के लिए उपयोग का मामला हो सकता है विंडोज़ ओएस के लिए भत्ते को छोड़कर, यहां मेरा सुझाव है:

 #!/usr/bin/env python3 # file: 'readchar.py' """ Implementation of a way to get a single character of input without waiting for the user to hit <Enter>. (OS is Linux, Ubuntu 14.04) """ import tty, sys, termios class ReadChar(): def __enter__(self): self.fd = sys.stdin.fileno() self.old_settings = termios.tcgetattr(self.fd) tty.setraw(sys.stdin.fileno()) return sys.stdin.read(1) def __exit__(self, type, value, traceback): termios.tcsetattr(self.fd, termios.TCSADRAIN, self.old_settings) def test(): while True: with ReadChar() as rc: char = rc if ord(char) <= 32: print("You entered character with ordinal {}."\ .format(ord(char))) else: print("You entered character '{}'."\ .format(char)) if char in "^C^D": sys.exit() if __name__ == "__main__": test() 

यहां दिए गए उत्तर जानकारीपूर्ण थे, हालांकि मैं अलग-अलग कार्यक्रमों में प्रमुख प्रेस को असिंक्रोनस रूप से कुंजी दबाने और आग से आग लगाने का एक तरीका चाहता हूं, सभी एक धागा-सुरक्षित, क्रॉस-प्लेटफ़ॉर्म तरीके से। मेरे लिए भी PyGame बहुत फूला हुआ था इसलिए मैंने निम्नलिखित (पायथन 2.7 में बनाया है लेकिन मुझे संदेह है कि यह आसानी से पोर्टेबल है), जो मुझे लगा कि मैं यहाँ साझा करता हूं अगर यह किसी और के लिए उपयोगी था मैंने इसे keyPress.py नामक एक फ़ाइल में संग्रहीत किया था।

 class _Getch: """Gets a single character from standard input. Does not echo to the screen. From http://code.activestate.com/recipes/134892/""" def __init__(self): try: self.impl = _GetchWindows() except ImportError: try: self.impl = _GetchMacCarbon() except(AttributeError, ImportError): self.impl = _GetchUnix() def __call__(self): return self.impl() class _GetchUnix: def __init__(self): import tty, sys, termios # import termios now or else you'll get the Unix version on the Mac def __call__(self): import sys, tty, termios fd = sys.stdin.fileno() old_settings = termios.tcgetattr(fd) try: tty.setraw(sys.stdin.fileno()) ch = sys.stdin.read(1) finally: termios.tcsetattr(fd, termios.TCSADRAIN, old_settings) return ch class _GetchWindows: def __init__(self): import msvcrt def __call__(self): import msvcrt return msvcrt.getch() class _GetchMacCarbon: """ A function which returns the current ASCII key that is down; if no ASCII key is down, the null string is returned. The page http://www.mactech.com/macintosh-c/chap02-1.html was very helpful in figuring out how to do this. """ def __init__(self): import Carbon Carbon.Evt #see if it has this (in Unix, it doesn't) def __call__(self): import Carbon if Carbon.Evt.EventAvail(0x0008)[0]==0: # 0x0008 is the keyDownMask return '' else: # # The event contains the following info: # (what,msg,when,where,mod)=Carbon.Evt.GetNextEvent(0x0008)[1] # # The message (msg) contains the ASCII char which is # extracted with the 0x000000FF charCodeMask; this # number is converted to an ASCII character with chr() and # returned # (what,msg,when,where,mod)=Carbon.Evt.GetNextEvent(0x0008)[1] return chr(msg & 0x000000FF) import threading # From https://stackoverflow.com/a/2022629/2924421 class Event(list): def __call__(self, *args, **kwargs): for f in self: f(*args, **kwargs) def __repr__(self): return "Event(%s)" % list.__repr__(self) def getKey(): inkey = _Getch() import sys for i in xrange(sys.maxint): k=inkey() if k<>'':break return k class KeyCallbackFunction(): callbackParam = None actualFunction = None def __init__(self, actualFunction, callbackParam): self.actualFunction = actualFunction self.callbackParam = callbackParam def doCallback(self, inputKey): if not self.actualFunction is None: if self.callbackParam is None: callbackFunctionThread = threading.Thread(target=self.actualFunction, args=(inputKey,)) else: callbackFunctionThread = threading.Thread(target=self.actualFunction, args=(inputKey,self.callbackParam)) callbackFunctionThread.daemon = True callbackFunctionThread.start() class KeyCapture(): gotKeyLock = threading.Lock() gotKeys = [] gotKeyEvent = threading.Event() keyBlockingSetKeyLock = threading.Lock() addingEventsLock = threading.Lock() keyReceiveEvents = Event() keysGotLock = threading.Lock() keysGot = [] keyBlockingKeyLockLossy = threading.Lock() keyBlockingKeyLossy = None keyBlockingEventLossy = threading.Event() keysBlockingGotLock = threading.Lock() keysBlockingGot = [] keyBlockingGotEvent = threading.Event() wantToStopLock = threading.Lock() wantToStop = False stoppedLock = threading.Lock() stopped = True isRunningEvent = False getKeyThread = None keyFunction = None keyArgs = None # Begin capturing keys. A seperate thread is launched that # captures key presses, and then these can be received via get, # getAsync, and adding an event via addEvent. Note that this # will prevent the system to accept keys as normal (say, if # you are in a python shell) because it overrides that key # capturing behavior. # If you start capture when it's already been started, a # InterruptedError("Keys are still being captured") # will be thrown # Note that get(), getAsync() and events are independent, so if a key is pressed: # # 1: Any calls to get() that are waiting, with lossy on, will return # that key # 2: It will be stored in the queue of get keys, so that get() with lossy # off will return the oldest key pressed not returned by get() yet. # 3: All events will be fired with that key as their input # 4: It will be stored in the list of getAsync() keys, where that list # will be returned and set to empty list on the next call to getAsync(). # get() call with it, aand add it to the getAsync() list. def startCapture(self, keyFunction=None, args=None): # Make sure we aren't already capturing keys self.stoppedLock.acquire() if not self.stopped: self.stoppedLock.release() raise InterruptedError("Keys are still being captured") return self.stopped = False self.stoppedLock.release() # If we have captured before, we need to allow the get() calls to actually # wait for key presses now by clearing the event if self.keyBlockingEventLossy.is_set(): self.keyBlockingEventLossy.clear() # Have one function that we call every time a key is captured, intended for stopping capture # as desired self.keyFunction = keyFunction self.keyArgs = args # Begin capturing keys (in a seperate thread) self.getKeyThread = threading.Thread(target=self._threadProcessKeyPresses) self.getKeyThread.daemon = True self.getKeyThread.start() # Process key captures (in a seperate thread) self.getKeyThread = threading.Thread(target=self._threadStoreKeyPresses) self.getKeyThread.daemon = True self.getKeyThread.start() def capturing(self): self.stoppedLock.acquire() isCapturing = not self.stopped self.stoppedLock.release() return isCapturing # Stops the thread that is capturing keys on the first opporunity # has to do so. It usually can't stop immediately because getting a key # is a blocking process, so this will probably stop capturing after the # next key is pressed. # # However, Sometimes if you call stopCapture it will stop before starting capturing the # next key, due to multithreading race conditions. So if you want to stop capturing # reliably, call stopCapture in a function added via addEvent. Then you are # guaranteed that capturing will stop immediately after the rest of the callback # functions are called (before starting to capture the next key). def stopCapture(self): self.wantToStopLock.acquire() self.wantToStop = True self.wantToStopLock.release() # Takes in a function that will be called every time a key is pressed (with that # key passed in as the first paramater in that function) def addEvent(self, keyPressEventFunction, args=None): self.addingEventsLock.acquire() callbackHolder = KeyCallbackFunction(keyPressEventFunction, args) self.keyReceiveEvents.append(callbackHolder.doCallback) self.addingEventsLock.release() def clearEvents(self): self.addingEventsLock.acquire() self.keyReceiveEvents = Event() self.addingEventsLock.release() # Gets a key captured by this KeyCapture, blocking until a key is pressed. # There is an optional lossy paramater: # If True all keys before this call are ignored, and the next pressed key # will be returned. # If False this will return the oldest key captured that hasn't # been returned by get yet. False is the default. def get(self, lossy=False): if lossy: # Wait for the next key to be pressed self.keyBlockingEventLossy.wait() self.keyBlockingKeyLockLossy.acquire() keyReceived = self.keyBlockingKeyLossy self.keyBlockingKeyLockLossy.release() return keyReceived else: while True: # Wait until a key is pressed self.keyBlockingGotEvent.wait() # Get the key pressed readKey = None self.keysBlockingGotLock.acquire() # Get a key if it exists if len(self.keysBlockingGot) != 0: readKey = self.keysBlockingGot.pop(0) # If we got the last one, tell us to wait if len(self.keysBlockingGot) == 0: self.keyBlockingGotEvent.clear() self.keysBlockingGotLock.release() # Process the key (if it actually exists) if not readKey is None: return readKey # Exit if we are stopping self.wantToStopLock.acquire() if self.wantToStop: self.wantToStopLock.release() return None self.wantToStopLock.release() def clearGetList(self): self.keysBlockingGotLock.acquire() self.keysBlockingGot = [] self.keysBlockingGotLock.release() # Gets a list of all keys pressed since the last call to getAsync, in order # from first pressed, second pressed, .., most recent pressed def getAsync(self): self.keysGotLock.acquire(); keysPressedList = list(self.keysGot) self.keysGot = [] self.keysGotLock.release() return keysPressedList def clearAsyncList(self): self.keysGotLock.acquire(); self.keysGot = [] self.keysGotLock.release(); def _processKey(self, readKey): # Append to list for GetKeyAsync self.keysGotLock.acquire() self.keysGot.append(readKey) self.keysGotLock.release() # Call lossy blocking key events self.keyBlockingKeyLockLossy.acquire() self.keyBlockingKeyLossy = readKey self.keyBlockingEventLossy.set() self.keyBlockingEventLossy.clear() self.keyBlockingKeyLockLossy.release() # Call non-lossy blocking key events self.keysBlockingGotLock.acquire() self.keysBlockingGot.append(readKey) if len(self.keysBlockingGot) == 1: self.keyBlockingGotEvent.set() self.keysBlockingGotLock.release() # Call events added by AddEvent self.addingEventsLock.acquire() self.keyReceiveEvents(readKey) self.addingEventsLock.release() def _threadProcessKeyPresses(self): while True: # Wait until a key is pressed self.gotKeyEvent.wait() # Get the key pressed readKey = None self.gotKeyLock.acquire() # Get a key if it exists if len(self.gotKeys) != 0: readKey = self.gotKeys.pop(0) # If we got the last one, tell us to wait if len(self.gotKeys) == 0: self.gotKeyEvent.clear() self.gotKeyLock.release() # Process the key (if it actually exists) if not readKey is None: self._processKey(readKey) # Exit if we are stopping self.wantToStopLock.acquire() if self.wantToStop: self.wantToStopLock.release() break self.wantToStopLock.release() def _threadStoreKeyPresses(self): while True: # Get a key readKey = getKey() # Run the potential shut down function if not self.keyFunction is None: self.keyFunction(readKey, self.keyArgs) # Add the key to the list of pressed keys self.gotKeyLock.acquire() self.gotKeys.append(readKey) if len(self.gotKeys) == 1: self.gotKeyEvent.set() self.gotKeyLock.release() # Exit if we are stopping self.wantToStopLock.acquire() if self.wantToStop: self.wantToStopLock.release() self.gotKeyEvent.set() break self.wantToStopLock.release() # If we have reached here we stopped capturing # All we need to do to clean up is ensure that # all the calls to .get() now return None. # To ensure no calls are stuck never returning, # we will leave the event set so any tasks waiting # for it immediately exit. This will be unset upon # starting key capturing again. self.stoppedLock.acquire() # We also need to set this to True so we can start up # capturing again. self.stopped = True self.stopped = True self.keyBlockingKeyLockLossy.acquire() self.keyBlockingKeyLossy = None self.keyBlockingEventLossy.set() self.keyBlockingKeyLockLossy.release() self.keysBlockingGotLock.acquire() self.keyBlockingGotEvent.set() self.keysBlockingGotLock.release() self.stoppedLock.release() 

विचार यह है कि आप या तो बस keyPress.getKey() कॉल कर सकते हैं, जो कुंजीपटल से एक कुंजी पढ़ेंगे, फिर इसे वापस लौटेंगे।

यदि आप उससे कुछ और चाहते हैं, तो मैंने एक KeyCapture ऑब्जेक्ट बनाया है। आप की तरह कुछ के माध्यम से एक बना सकते हैं keys = keyPress.KeyCapture()

फिर तीन चीजें हैं जो आप कर सकते हैं:

addEvent(functionName) किसी भी फ़ंक्शन में लेता है जो एक पैरामीटर में ले जाता है। फिर हर बार एक कुंजी दबाई जाती है, इस फ़ंक्शन को उस कुंजी की स्ट्रिंग के साथ बुलाया जाएगा क्योंकि यह इनपुट है ये एक अलग धागे में भाग जाते हैं, इसलिए आप उन सभी को ब्लॉक कर सकते हैं जो आप चाहते हैं और यह KeyCapturer की कार्यक्षमता को गड़बड़ नहीं करेगा और न ही अन्य ईवेंट में देरी करेगा

पहले से ही अवरुद्ध तरीके से कुंजी get() अब इसकी आवश्यकता यहां है क्योंकि चाबियाँ अब KeyCapture ऑब्जेक्ट के माध्यम से कैप्चर की जा रही हैं, इसलिए keyPress.getKey() उस व्यवहार से विरोधाभासी होगी और उनमें से कुछ चाबियाँ खो देंगे क्योंकि केवल एक कुंजी को एक समय में कैप्चर किया जा सकता है। इसके अलावा, कहें कि उपयोगकर्ता प्रेस 'ए', फिर 'बी', आप कॉल get() करते हैं, उपयोगकर्ता प्रेस 'सी' वह get() कॉल तुरंत 'ए' लौटाएगा, फिर अगर आप इसे फिर से कहते हैं तो यह 'बी', फिर 'सी' लौटाएगा यदि आप इसे फिर से कॉल करते हैं तो इसे एक दूसरे की दबाए जाने तक रोक दिया जाएगा। इससे यह सुनिश्चित होता है कि अगर कोई वांछित हो, तो किसी अवरुद्ध तरीके से आप किसी भी चाबियाँ नहीं छोड़ें। तो इस तरह से यह पहले से keyPress.getKey() तुलना में थोड़ा अलग है

यदि आप getKey() वापस का व्यवहार चाहते हैं, तो get(lossy=True) get() , सिवाय इसके कि यह केवल कॉल get() करने के बाद दबाए गए कुंजी वापस करता है get() । इसलिए उपर्युक्त उदाहरण में, get() उपयोगकर्ता प्रेस 'सी' तक ब्लॉक हो जाएगा, और फिर अगर आप इसे फिर से कहते हैं तो इसे एक दूसरे की दबाए जाने तक रोक दिया जाएगा।

getAsync() थोड़ा अलग है यह कुछ ऐसी चीज़ों के लिए डिज़ाइन किया गया है जो कई प्रसंस्करण करता है, फिर कभी-कभी वापस आ जाता है और जांचता है कि कौन सी कुंजी दबाई गई थी। इस प्रकार getAsync() करने के अंतिम कॉल के बाद दबाए गए सभी getAsync() एक सूची लौटाता है, क्रम में सबसे पुरानी कुंजी दबाए जाने के लिए हाल ही की कुंजी दबाया जाता है यह भी ब्लॉक नहीं करता है, जिसका अर्थ है कि अगर getAsync() को getAsync() करने के अंतिम कॉल के बाद कोई चाबियाँ नहीं दबाई जाती हैं, तो खाली [] लौटा दिया जाएगा

वास्तव में चाबियाँ कैप्चर करने के लिए, आपको अपनी keys ऑब्जेक्ट के साथ keys.startCapture() कॉल करने की आवश्यकता है। keys.startCapture() startCapture गैर-अवरुद्ध है, और केवल एक धागा शुरू करता है जो कि कुंजी प्रेस को रिकॉर्ड करता है, और एक अन्य धागा उन प्रमुख प्रेस यह सुनिश्चित करने के लिए दो धागे हैं कि प्रमुख प्रेस रिकॉर्ड करने वाला थ्रेड किसी भी कुंजी को नहीं भुलाता है।

यदि आप कुंजी कैप्चर करना बंद करना चाहते हैं, तो आप चाबियाँ कॉल कर सकते हैं। keys.stopCapture() और यह कुंजी कैप्चरिंग बंद कर देगी। हालांकि, एक कुंजी को कैप्चर करने से एक ब्लॉकिंग ऑपरेशन होता है, थ्रेड कैप्चरिंग कीज़ को stopCapture() कॉल करने के बाद एक और कुंजी को कैप्चर कर सकता है।

इसे रोकने के लिए, आप एक वैकल्पिक पैरामीटर ( startCapture(functionName, args) को एक समारोह की startCapture(functionName, args) में पारित कर सकते हैं जो कि चेक की तरह कुछ करता है यदि कोई चाबी 'c' के बराबर होती है और फिर बाहर निकलती है यह महत्वपूर्ण है कि यह फ़ंक्शन बहुत कम समय पहले करता है, उदाहरण के लिए, यहां एक नींद हमें कुंजियों को याद करने के लिए कारण देगा।

हालांकि, यदि stopCapture() को इस फ़ंक्शन में कहा जाता है, तो किसी भी अधिक कब्जा करने की कोशिश किए बिना, कुंजी कैप्चर तुरंत बंद हो जाएंगे, और सभी get() कॉल्स तत्काल वापस कर दिए जाएंगे, कोई भी नहीं, अगर कोई चाबियाँ अभी तक दबाई नहीं गई हैं।

साथ ही, चूंकि दबाए गए सभी पिछली कुंजियों को get() और getAsync() जब तक आप उन्हें पुनः प्राप्त नहीं करते हैं), आप clearGetList() और clearAsyncList() को पहले दबाए गए कुंजी को भूल सकते हैं।

ध्यान दें कि get() , getAsync() और घटनाएं स्वतंत्र हैं, इसलिए यदि कोई कुंजी दबायी जाती है: 1. एक कॉल get() जो कि इंतजार कर रही है, उस पर हानिपूर्ण होने पर, वह कुंजी वापस आ जाएगी अन्य प्रतीक्षा कॉल (यदि कोई हो) प्रतीक्षा करते रहेंगे 2. उस कुंजी को प्राप्त की कतारों में संग्रहित किया जाएगा, जिससे कि get() हानिकारक get() साथ get() हो जाएगा पुरानी कुंजी को वापस get() अभी तक get() नहीं get() दबाया जाएगा। 3. सभी घटनाओं को उस कुंजी के साथ उनके इनपुट के रूप में निकाल दिया जाएगा 4. उस कुंजी को getAsync() की सूची में संग्रहित किया जाएगा, जहां उस getAsync() टवील को लौटा दिया जाएगा और अगली कॉल में खाली getAsync()

यदि यह सब बहुत अधिक है, तो यहां एक उदाहरण का प्रयोग किया गया है:

 import keyPress import time import threading def KeyPressed(k, printLock): printLock.acquire() print "Event: " + k printLock.release() time.sleep(4) printLock.acquire() print "Event after delay: " + k printLock.release() def GetKeyBlocking(keys, printLock): while keys.capturing(): keyReceived = keys.get() time.sleep(1) printLock.acquire() if not keyReceived is None: print "Block " + keyReceived else: print "Block None" printLock.release() def GetKeyBlockingLossy(keys, printLock): while keys.capturing(): keyReceived = keys.get(lossy=True) time.sleep(1) printLock.acquire() if not keyReceived is None: print "Lossy: " + keyReceived else: print "Lossy: None" printLock.release() def CheckToClose(k, (keys, printLock)): printLock.acquire() print "Close: " + k printLock.release() if k == "c": keys.stopCapture() printLock = threading.Lock() print "Press a key:" print "You pressed: " + keyPress.getKey() print "" keys = keyPress.KeyCapture() keys.addEvent(KeyPressed, printLock) print "Starting capture" keys.startCapture(CheckToClose, (keys, printLock)) getKeyBlockingThread = threading.Thread(target=GetKeyBlocking, args=(keys, printLock)) getKeyBlockingThread.daemon = True getKeyBlockingThread.start() getKeyBlockingThreadLossy = threading.Thread(target=GetKeyBlockingLossy, args=(keys, printLock)) getKeyBlockingThreadLossy.daemon = True getKeyBlockingThreadLossy.start() while keys.capturing(): keysPressed = keys.getAsync() printLock.acquire() if keysPressed != []: print "Async: " + str(keysPressed) printLock.release() time.sleep(1) print "done capturing" 

यह मेरे द्वारा किए गए साधारण परीक्षण से मेरे लिए अच्छी तरह से काम कर रहा है, लेकिन मुझे खुशी है कि मैं दूसरों की राय भी ले सकता हूं अगर मुझे कुछ याद आ गया है।

मैंने इसे यहाँ भी पोस्ट किया।

यह गैर-अवरोधन है, एक कुंजी को पढ़ता है और उसे कुंजीप्रेसी.की में संग्रहीत करता है।

 import Tkinter as tk class Keypress: def __init__(self): self.root = tk.Tk() self.root.geometry('300x200') self.root.bind('<KeyPress>', self.onKeyPress) def onKeyPress(self, event): self.key = event.char def __eq__(self, other): return self.key == other def __str__(self): return self.key 

आपके प्रोग्राम में

 keypress = Keypress() while something: do something if keypress == 'c': break elif keypress == 'i': print('info') else: print("i dont understand %s" % keypress) 

कच्चे_इनपुट के निर्माण में मदद करनी चाहिए

 for i in range(3): print ("So much work to do!") k = raw_input("Press any key to continue...") print ("Ok, back to work.") 

पैगमेम के साथ इस कोशिश करो:

 import pygame pygame.init() // eliminate error, pygame.error: video system not initialized keys = pygame.key.get_pressed() if keys[pygame.K_SPACE]: d = "space key" print "You pressed the", d, "." 

Try using this: http://home.wlu.edu/~levys/software/kbhit.py It's non-blocking (that means that you can have a while loop and detect a key press without stopping it) and cross-platform.

 import os # Windows if os.name == 'nt': import msvcrt # Posix (Linux, OS X) else: import sys import termios import atexit from select import select class KBHit: def __init__(self): '''Creates a KBHit object that you can call to do various keyboard things.''' if os.name == 'nt': pass else: # Save the terminal settings self.fd = sys.stdin.fileno() self.new_term = termios.tcgetattr(self.fd) self.old_term = termios.tcgetattr(self.fd) # New terminal setting unbuffered self.new_term[3] = (self.new_term[3] & ~termios.ICANON & ~termios.ECHO) termios.tcsetattr(self.fd, termios.TCSAFLUSH, self.new_term) # Support normal-terminal reset at exit atexit.register(self.set_normal_term) def set_normal_term(self): ''' Resets to normal terminal. On Windows this is a no-op. ''' if os.name == 'nt': pass else: termios.tcsetattr(self.fd, termios.TCSAFLUSH, self.old_term) def getch(self): ''' Returns a keyboard character after kbhit() has been called. Should not be called in the same program as getarrow(). ''' s = '' if os.name == 'nt': return msvcrt.getch().decode('utf-8') else: return sys.stdin.read(1) def getarrow(self): ''' Returns an arrow-key code after kbhit() has been called. Codes are 0 : up 1 : right 2 : down 3 : left Should not be called in the same program as getch(). ''' if os.name == 'nt': msvcrt.getch() # skip 0xE0 c = msvcrt.getch() vals = [72, 77, 80, 75] else: c = sys.stdin.read(3)[2] vals = [65, 67, 66, 68] return vals.index(ord(c.decode('utf-8'))) def kbhit(self): ''' Returns True if keyboard character was hit, False otherwise. ''' if os.name == 'nt': return msvcrt.kbhit() else: dr,dw,de = select([sys.stdin], [], [], 0) return dr != [] 

An example to use this:

 import kbhit kb = kbhit.KBHit() while(True): print("Key not pressed") #Do something if kb.kbhit(): #If a key is pressed: k_in = kb.getch() #Detect what key was pressed print("You pressed ", k_in, "!") #Do something kb.set_normal_term() 

Or you could use the getch module from PyPi . But this would block the while loop

The curses package in python can be used to enter "raw" mode for character input from the terminal with just a few statements. Curses' main use is to take over the screen for output, which may not be what you want. This code snippet uses print() statements instead, which are usable, but you must be aware of how curses changes line endings attached to output.

 #!/usr/bin/python3 # Demo of single char terminal input in raw mode with the curses package. import sys, curses def run_one_char(dummy): 'Run until a carriage return is entered' char = ' ' print('Welcome to curses', flush=True) while ord(char) != 13: char = one_char() def one_char(): 'Read one character from the keyboard' print('\r? ', flush= True, end = '') ## A blocking single char read in raw mode. char = sys.stdin.read(1) print('You entered %s\r' % char) return char ## Must init curses before calling any functions curses.initscr() ## To make sure the terminal returns to its initial settings, ## and to set raw mode and guarantee cleanup on exit. curses.wrapper(run_one_char) print('Curses be gone!') 

A comment in one of the other answers mentioned cbreak mode, which is important for Unix implementations because you generally don't want ^C ( KeyboardError ) to be consumed by getchar (as it will when you set the terminal to raw mode, as done by most other answers).

Another important detail is that if you're looking to read one character and not one byte , you should read 4 bytes from the input stream, as that's the maximum number of bytes a single character will consist of in UTF-8 (Python 3+). Reading only a single byte will produce unexpected results for multi-byte characters such as keypad arrows.

Here's my changed implementation for Unix:

 import contextlib import os import sys import termios import tty _MAX_CHARACTER_BYTE_LENGTH = 4 @contextlib.contextmanager def _tty_reset(file_descriptor): """ A context manager that saves the tty flags of a file descriptor upon entering and restores them upon exiting. """ old_settings = termios.tcgetattr(file_descriptor) try: yield finally: termios.tcsetattr(file_descriptor, termios.TCSADRAIN, old_settings) def get_character(file=sys.stdin): """ Read a single character from the given input stream (defaults to sys.stdin). """ file_descriptor = file.fileno() with _tty_reset(file_descriptor): tty.setcbreak(file_descriptor) return os.read(file_descriptor, _MAX_CHARACTER_BYTE_LENGTH) 

My solution for python3, not depending on any pip packages.

 # precondition: import tty, sys def query_yes_no(question, default=True): """ Ask the user a yes/no question. Returns immediately upon reading one-char answer. Accepts multiple language characters for yes/no. """ if not sys.stdin.isatty(): return default if default: prompt = "[Y/n]?" other_answers = "n" else: prompt = "[y/N]?" other_answers = "yjosiá" print(question,prompt,flush= True,end=" ") oldttysettings = tty.tcgetattr(sys.stdin.fileno()) try: tty.setraw(sys.stdin.fileno()) return not sys.stdin.read(1).lower() in other_answers except: return default finally: tty.tcsetattr(sys.stdin.fileno(), tty.TCSADRAIN , oldttysettings) sys.stdout.write("\r\n") tty.tcdrain(sys.stdin.fileno()) 

I believe that this is one the most elegant solution.

 import os if os.name == 'nt': import msvcrt def getch(): return msvcrt.getch().decode() else: import sys, tty, termios fd = sys.stdin.fileno() old_settings = termios.tcgetattr(fd) def getch(): try: tty.setraw(sys.stdin.fileno()) ch = sys.stdin.read(1) finally: termios.tcsetattr(fd, termios.TCSADRAIN, old_settings) return ch 

and then use it in the code:

 if getch() == chr(ESC_ASCII_VALUE): print("ESC!")