I am working on a typing game in Python that uses getch() to read in characters, then performs different actions depending on which character has been entered.

The code for reading in characters and assigning them to bytestrings (if needed) is as follows:

character = getch() # Imported via pip install py-getch
# character is returned as a bytestring on 
# Windows but a string in Linux, so I added in 
# the following if statement to resolve this 
# difference.
if type(character) == str:
    character = character.encode() 

In the Windows terminal, if I enter a backspace, the value of character becomes b'\x08'. Meanwhile, if I hit Ctrl + Backspace, b'\x7f' gets stored in `character.'

However, I found that, in my Ubuntu terminal, these bytestrings are reversed: a regular backspace (after it gets encoded) returns b'\x7f' whereas Ctrl + Backspace returns b'\x08'. This means that, without adjusting for the player's OS, hitting backspace will cause my program to delete one character in Windows but an entire word in Linux.

Does this reflect normal behavior on these two operating systems, or could there be something unusual about my setup or code that is causing this difference?

I'm currently resolving this issue by checking the player's platform, then using that information to determine which bytestrings to map to 'character_backspace' and 'word_backspace'. I can then have the script delete single characters or entire words, respectively, if the character input by the player matches one of these variables.

Here's the code I'm using:

import platform
if platform.system() == 'Linux':
    character_backspace = b'\x7f'
    word_backspace = b'\x08'
else:
    character_backspace = b'\x08'
    word_backspace = b'\x7f'

(I haven't tested this behavior on a Mac, so I may need to update the code depending on which bytestrings get produced by Backspace and Command + Backspace on that system.)

This approach works for my needs, but is there a more elegant solution that prevents the code from having to check the player's platform in the first place?

1

There are 1 best solutions below

0
n. m. could be an AI On

On Linux, the following facts are true by default:

  • The backspace key of the PC keyboard generates ASCII DEL character (other keyboard models may behave differently)
  • ASCII DEL character, when typed while editing, erases the last character
  • Ctrl+W, when typed while editing, erases the last word
  • Ctrl-H a.k.a. ASCII BS character doesn't perform any editing function

All of this is done at the kernel level and have nothing to do with Python. Python just sends you whatever the OS sends it. Note, programs that incorporate their own editing functionality such as bash or vim may assign these characters different editing functions.

These defaults can be globally changed, but such change may change behaviour of other programs.

I would recommend adding a configurable keyboard map to your program. This way, users may configure exactly what they want, even if they have weird defaults or non-standard keyboards.