Как прочитать один char с консоли в Java (как пользователь вводит его)?
Есть ли простой способ прочитать один char с консоли, когда пользователь вводит его в Java? Является ли это возможным? Я пробовал эти методы, но все они ждут нажатия клавиши ввода:
char tmp = (char) System.in.read();
char tmp = (char) new InputStreamReader(System.in).read ();
char tmp = (char) System.console().reader().read(); // Java 6
Я начинаю думать, что System.in не знает ввода пользователя, пока не будет нажата клавиша.
Ответы
Ответ 1
То, что вы хотите сделать, это перевести консоль в "сырой" режим (отредактированное редактирование линии и не требуется вводить ключ) в отличие от "приготовленного" режима (редактирование строки с требуемым ключом ввода). В системах UNIX команда "stty" может изменить режимы.
Теперь, в отношении Java... см. Неблокирующий ввод консоли в Python и Java. Выдержка:
Если ваша программа должна быть консольной, вам необходимо переключить свой терминал из линейного режима в режим символов и не забудьте восстановить его до выхода из программы. В операционных системах нет портативного способа сделать это.
Одним из предложений является использование JNI. Опять же, это не очень портативно. Другое предложение в конце потока, и вместе с вышеприведенным сообщением, - это посмотреть на использование jCurses.
Ответ 2
Вам нужно перевести консоль в режим raw. Нет встроенного независимого от платформы способа добраться туда. Хотя курсы могут быть интересными.
В системе Unix это может работать:
String[] cmd = {"/bin/sh", "-c", "stty raw </dev/tty"};
Runtime.getRuntime().exec(cmd).waitFor();
Например, если вы хотите учесть время между нажатиями клавиш, здесь приведен пример кода, чтобы добраться туда.
Ответ 3
Нет портативного способа чтения необработанных символов с консоли Java.
Некоторые связанные с платформой обходные решения были представлены выше. Но чтобы быть действительно портативным, вам придется отказаться от консольного режима и использовать режим окон, например. AWT или Swing.
Ответ 4
Я написал Java-класс RawConsoleInput, который использует JNA для вызова функций операционной системы Windows и Unix/Linux.
- В Windows он использует
_kbhit()
и _getwch()
из msvcrt.dll. - В Unix он использует
tcsetattr()
для переключения консоли в неканонический режим System.in.available()
чтобы проверить, доступны ли данные, и System.in.read()
для чтения байтов из консоли. CharsetDecoder
используется для преобразования байтов в символы.
Он поддерживает неблокирующий входной и смешанный режим raw и обычный вход в линейный режим.
Ответ 5
Использовать jline3:
Пример:
Terminal terminal = TerminalBuilder.builder()
.jna(true)
.system(true)
.build();
// raw mode means we get keypresses rather than line buffered input
terminal.enterRawMode();
reader = terminal .reader();
...
int read = reader.read();
....
reader.close();
terminal.close();