특정 키보드 단축키에 대한 문자 시퀀스를 얻으려면 showkey -a
그대로( Ctrl+ V)를 사용하거나 삽입합니다.
그 반대는 무엇입니까? 사람이 읽을 수 있는 형식의 문자 시퀀스에서 키보드 단축키를 얻는 방법은 무엇입니까?
예를 들어 몇 가지 키 바인딩을 사용했습니다.
^[^?
^X^U
^[[3;5~
^[[1;2D
^[[1;2C
^[[1;5C
^[[1;5D
^[[1;6C
^[[1;6D
....
이제 어떤 키/키 조합을 사용했는지 기억이 나지 않습니다.
어떻게 찾을 수 있나요?
업데이트 1
나는 사람이 읽을 수 있는 형식으로 등을 출력할 수 있는 Ctrl+R
것을 찾고 있습니다 .Ctrl+Delete
가능한 문자 시퀀스와 사람이 읽을 수 있는 형식이 포함된 테이블에 대한 참조도 괜찮습니다.
답변1
처음 몇 줄
^[^?
^X^U
ASCII 컨트롤로 나열된 코드를 찾을 수 있습니다.
^[ (escape)
^U (control-U)
^X (control-X)
저것^?
ASCII DEL의 정규 표현입니다(삭제열쇠).
단말기 설명( TERM
)이 올바르게 설정되었다면,
infocmp -1 -x
키의 ncurses 이름은 terminfo 형식으로 인쇄됩니다. 추가 정보가 있지만 다음 줄이 표시됩니다.
kDC5=\E[3;5~,
kRIT=\E[1;2C,
kRIT3=\E[1;3C,
kRIT4=\E[1;4C,
kRIT5=\E[1;5C,
kRIT6=\E[1;6C,
kRIT7=\E[1;7C,
kLFT=\E[1;2D,
kLFT3=\E[1;3D,
kLFT4=\E[1;4D,
kLFT5=\E[1;5D,
kLFT6=\E[1;6D,
kLFT7=\E[1;7D,
어디에 (주어진 용어 정보\E
ASCII 이스케이프 처리되었거나^[
) 귀하의 예에 해당한다고 생각할 수 있습니다. 이것kLFT
그리고kRIT
이름을 보면 어떤 것이 무엇인지 알 수 있습니다(xterm-style).수정됨왼쪽/오른쪽 커서 키(참조XTerm 제어 순서이름 뒤의 숫자의 의미는 코드/수정자 표를 참조하세요. terminfo 이름은 다음에 나열되어 있습니다.터미널 데이터베이스:
# These are the extended keys defined in this file:
#
# kDC3 kDC4 kDC5 kDC6 kDC7 kDN kDN3 kDN4 kDN5 kDN6 kDN7 kEND3 kEND4 kEND5 kEND6
# kEND7 kHOM3 kHOM4 kHOM5 kHOM6 kHOM7 kIC3 kIC4 kIC5 kIC6 kIC7 kLFT3 kLFT4
# kLFT5 kLFT6 kLFT7 kNXT3 kNXT4 kNXT5 kNXT6 kNXT7 kPRV3 kPRV4 kPRV5 kPRV6 kPRV7
# kRIT3 kRIT4 kRIT5 kRIT6 kRIT7 kUP kUP3 kUP4 kUP5 kUP6 kUP7 ka2 kb1 kb3 kc2
에 설명되어 있습니다.user_caps
맨 페이지.
이 모든 것을 염두에 두고 누군가가 다음을 표시하는 테이블을 만드는 프로그램이나 스크립트를 만들 수 있습니까?읽을 수 있는 형식(그러나 기록된 위치를 아는 것이 도움이 될 것입니다).
^[^?
일부 단말기에서는 을 누르면 이 정보가 전송됩니다 AltDelete(그러나 단말기 설명에는 없습니다). 이는 ^X^U
터미널 에뮬레이터에서 단일 키 누르기에 의해 전송되는 시퀀스가 아닙니다(바운스 키 누르기가 없는 한). 두 번의 키 누르기일 가능성이 높습니다.
답변2
터미널이 ECMA-48 형식, DECFNK, Interix, SCO 콘솔 또는 Unicode RXVT 형식으로 입력 제어 시퀀스를 생성하는 한 이를 내 console-decode-ecma48
도구에 제공하고 --input
명령줄 옵션을 사용하여 문자 스트림이 입력이 아닌 입력임을 알릴 수 있습니다. 출력 . 이는 오늘날 실제로 접하는 대부분의 터미널과 터미널 에뮬레이터에 해당됩니다.
입력 내용은 다음과 같습니다. ^[
물론 실제 문자로 대체됩니다.␛
%콘솔 디코딩 -ecma48 --input << EOF ^[^? ^X^U ^[[3;5~ ^[[1;2D ^[[1;2C ^[[1;5C ^[[1;5D ^[[1;6C ^[[1;6D EOF 델 만약에 U+00000015 만약에 DEC 제어+삭제 만약에 레벨 2+CUB 1 만약에 레벨 2+CUF 1 만약에 컨트롤+CUF 1 만약에 컨트롤+컵 1 만약에 컨트롤+레벨 2+CUF 1 만약에 컨트롤+레벨2+CUB 1 만약에 %
명시된 바와 같이https://unix.stackexchange.com/a/504056/5132⎇ Alt, 키 코드에 대한 일부 터미널 작업을 디코딩하려면반품이 --no-7bit
옵션은 필수입니다. 그렇지 않으면 C1 제어 문자의 7비트 별칭에 대한 ECMA-48 표준 디코딩을 얻게 됩니다.
CUF
CUB
물론 표준 ECMA-48 이름입니다.CURSOR에프앞으로" 그리고 "CURSOR두번째서투른". 매뉴얼을 참조하세요.
터미널 제어 시퀀스의 규칙은 여러분을 놀라게 할 수 있습니다. ␛
, DEL, ␊
및 ␘
을 입력했습니다 ␕
. 터미널 제어 시퀀스의 규칙은 다음과 같습니다.
␛
이스케이프 시퀀스를 시작합니다 .- DEL은 제어 문자로 즉시 처리되지만 이스케이프 시퀀스는 아직 보류 중입니다.
␊
제어 문자로 즉시 처리 되지만 이스케이프 시퀀스는 아직 보류 중입니다.- 보류 중인 이스케이프 시퀀스를 취소합니다
␘
(이름에 있음). ␕
C0 제어 문자로 처리됩니다 .console-decode-ecma48
해당 특정 문자에 대한 유니코드 코드 포인트를 인쇄합니다.
내가 아는 한 실제로 올바른 ECMA-48 디코더가 포함된 쉘은 없습니다. 셸은 패턴 일치를 수행하는데, 이는 터미널이 항상 보내는 실제 ECMA-48 인코딩 콘텐츠를 처리하는 데 있어 상당히 불완전합니다. 이로 인해 아래에서 설명하는 것과 같은 문제가 발생할 수 있습니다.https://unix.stackexchange.com/a/499139/5132그리고https://unix.stackexchange.com/a/520429/5132등.
console-decode-ecma48
실제로 SCO 콘솔, Interix 등과 달리 제어 시퀀스 상태 머신을 갖춘 적절한 ECMA-48 디코더가 있습니다. 그건 너한테 보여주지 않을 거야정확히GNU Readline, libedit 및 ZLE와 같은 작업이 입력에 수행되는 작업은 올바른 프로토콜을 얻지 못한다는 것입니다.
하지만 그것은~ 할 것이다ECMA-48 터미널이 전송 중이라고 생각하는 내용, 즉 정확히 사용자가 원하는 내용을 보여줍니다.
추가 읽기
- 조나단 데보인 폴라드(2018). "
console-decode-ecma48
". 스낵 가이드. 소프트웨어.
답변3
특정 키(또는 키 조합)를 누를 때 터미널이 전송하는 문자 또는 문자 시퀀스는 터미널 자체에 따라 다릅니다.
a
준범용이지만 키 A 를 누를 때 모든 터미널이 전송되지만(적어도 그러한 키가 있는 터미널의 경우) , 또는 Home+ Left와 같은 키의 경우 터미널마다 크게 다릅니다 .F1Ctrl6
그러나 몇 가지 공통점이 있습니다. 값이 0부터 31까지인 ASCII 제어 문자는 일반적으로 , ^@
... ^A
, ^Z
, ^[
, ^\
및 ]
로 표시됩니다 . 이들 모두에 대해 인쇄 가능한 문자의 비트 6을 전환하면 해당 제어 문자(예: 0x1 인 0x41)를 얻게 됩니다. 0x7f, 0x3f입니다.^^
^_
A
^A
^?
?
^X
+ 를 누르면 Ctrl터미널에서 문자를 보냅니다 X.
^I
TabTAB 제어 문자로, 제어 문자( Ctrl+ 제외)가 있는 I키를 누를 때도 전송됩니다 .
^[
, 일명 \e
및 Esc키 와 동일합니다.
^H
\b
백스페이스 문자 라고도 하지만 일부 터미널에서는 DEL
( ^?
)를 보내고 Backspace다른 터미널에서는 를 보내지 않습니다 ^H
.
^M
aka는 \r
Return/Enter 시 전송됩니다(그러나 일부 모드에서는 터미널 장치 드라이버에 의해 aka로 변환될 수 있음 ^J
).\n
^@
AKA는 \0
+로 보낼 수도 있지만, 가끔 +로 보낼 수도 있습니다.Ctrl@CtrlSpace
일부 터미널에는 다른 키와 결합할 때 비트 8이 설정된 동일한 문자를 보내는 Meta또는 수정자 키가 있습니다(예: + (없이 )는 0x61에서 바이트 0xE1을 보냅니다 ). 다른 것들은(지금은 더 일반적임) 문자 뒤에 전송되었을 문자 또는 문자 시퀀스를 보냅니다 (예: + send ).AltMetaAShifta
^[
MetaMetaA^[a
대부분의 다른 기능 키는 일반적으로 (ESC)로 시작하는 일련의 문자를 보냅니다 ^[
. 한 가지 예외는 Delete일부 터미널에서 DEL()을 보내는 것 입니다 ^?
.
이제 키보드 입력을 처리하는 터미널 애플리케이션은 터미널 장치로부터 일련의 문자를 수신할 때 해당하는 키 누르기를 알고 싶어합니다. 서로 다른 터미널이 서로 다른 시퀀스를 전송하면 어떻게 되나요?
여기서 $TERM
환경 변수가 작용합니다. 이 변수는 getty
터미널 에뮬레이터나 사용자가 애플리케이션에 통신 중인 터미널을 알려주기 위해 설정됩니다. 값은 터미널 유형을 고유하게 식별하는 짧은 이름입니다.
예를 들어 최신 xterm
터미널 에뮬레이터에서는 이를 xterm-256color
.
그런 다음 이러한 응용 프로그램은 이 값을 사용하여 터미널 설명 데이터베이스를 쿼리하여 터미널 기능에 대해 알아볼 수 있습니다. 예를 들어 다음과 같은 기능이 있을 수 있습니다. 문자의 순서는 무엇이어야 합니까?보내다터미널에서 활성화용감한텍스트 출력. 다른 것들은 응용프로그램이 사용할 일련의 문자일 수 있습니다.받다이 키를 누르면 터미널에서 Delete.
역사적으로 두 개의 기본 데이터베이스가 있었고 각각 termcap
에는 terminfo
쿼리를 위한 API 세트가 있었습니다. 요즘에는 terminfo
(더 발전된) 것이 일반적이고 ncurses
(만들어진)@토마스디키지난 수십 년 동안)은 상호 작용을 위한 범용 라이브러리입니다(동일한 백엔드를 사용하여 termcap 인터페이스도 노출함).
이제 가능한 세트능력이 데이터베이스의 저장소는 고정되어 있습니다. terminfo(5)
맨 페이지에 설명되어 있습니다 .
키 전면에는 제한된 수의 키가 덮여 있습니다. 우리 대부분이 들어본 적이 없는 키를 포함하여 여전히 큰 목록이지만 과거와 미래의 가능한 모든 터미널에 대한 모든 기능 키를 포함하지는 않습니다. 일부 키 조합(주로 Shift+ ) 을 다루지 SomeFuncKeys만 가능한 모든 조합(예: Ctrl+ Shift+ Up)을 다루지는 않습니다.
GNU 시스템에서는 다음을 참조하세요.
man 5 terminfo | grep -Po '^\s*\Kkey_.*'
목록을 위해.
이제 terminfo
셸에서 데이터베이스를 쿼리하려면 다음과 같은 3가지 주요 명령이 있습니다 ncurses
.
toe
: 데이터베이스의 터미널 나열tput
:원래 함수를 인쇄합니다. (보통 이스케이프 시퀀스를 보내는 데 사용됩니다. 예:tput bold
start용감한모델).infocmp
: 데이터베이스에서 전체 항목을 검색하거나 비교합니다.
여기서 후자는 어떤 터미널 키가 주어진 시퀀스를 보낼 수 있는지 알아내는 데 유용합니다. infocmp -xL1
즉, 줄당 및 ong(더 설명적인) 함수 이름과 함께 저장된 터미널(따라서 터미널)의 알려진 모든 기능에 대한 출력 식별자입니다. 그래서:$TERM
1
L
$ infocmp -xL1 | grep key_
key_b2=\EOE,
key_backspace=\177,
key_btab=\E[Z,
key_dc=\E[3~,
key_down=\EOB,
key_end=\EOF,
key_enter=\EOM,
[...]
알려진 모든 키에 대한 모든 시퀀스를 제공합니다.
내 xterm
터미널에는 다음이 표시됩니다.
key_sright=\E[1;2C,
key_sleft=\E[1;2D,
예를 들어.
쉘은 또한 특수 연관 배열 zsh
(해당 변수에 액세스할 때 자동으로 로드되는 모듈)에 현재 터미널의 기능을 노출합니다. 따라서 정보를 얻는 또 다른 방법은 다음과 같습니다.$terminfo
zsh/terminfo
$ key=$'\e[1;2D'
$ echo ${(k)terminfo[(Re)$key]}
kLFT
(이것은짧은terminfo 이름이 있습니다).
terminfo 데이터베이스는 내 터미널로 전송된 키를 나열하지 않지만 예를 들어 +, + 또는 + +를 입력하면 ^[^?
해당 시퀀스를 얻습니다.Esc Ctrl?Ctrl[ ?AltCtrl?
아마도 귀하의 터미널이 ^?
에 전송하고 있을 수도 있고, +에 이를 수신 Delete할 수도 있습니다 .MetaDelete
^X^U
CtrlX Ctrl++ 에 보낼 예정 U이라면 터미널에 해당 기능을 보내는 기능 키가 있을 것이라고는 상상할 수 없지만 많은 터미널 에뮬레이터에서는 모든 문자 시퀀스를 모든 키 또는 키 조합에 바인딩할 수 있습니다.
1 터미널은 입력 시 특정 기능 키에 대해 서로 다른 시퀀스를 보낼 수 있으므로 많은 터미널에는 추가적인 주의 사항이 있습니다.키보드 적용 모드그리고 그렇지 않을 때. 이 경우 terminfo 항목은 다음을 설명합니다.키보드 적용 모드. 애플리케이션은 이 함수에 해당하는 시퀀스를 전송하여 터미널을 이 모드로 전환할 수 있습니다 smkx
.
답변4
세게 때리다
$ bind -p | grep -F '[3;5~'
"\e[3;5~": delete-char