어떤 키를 눌렀습니까?


15

이 작업은 키보드에서 누른 키를 식별하는 코드를 작성하는 것입니다. 한 번에 하나의 키만 눌렀으며 표준 미국 키보드 레이아웃이 있다고 가정 할 수 있습니다. 이것이 2보다 @가있는 레이아웃입니다.

코드는 누른 키에 대한 고유 식별자를 출력해야합니다. 여기에는 PrtScn, Scroll Lock, Pause, 왼쪽 Shift, 오른쪽 Shift, 왼쪽 Ctrl, 오른쪽 Ctrl, Caps Lock, Tab, Enter, 숫자 키패드 입력, 숫자 잠금, 삽입, 숫자 패드 입력, 백 스페이스, Del, F1이 포함됩니다. ... F12, Esc, 왼쪽 Windows 키, 오른쪽 Windows 키, Alt, AltGr, 응용 프로그램 키 (컨텍스트 메뉴) 등.

코드는 키를 누를 때까지 기다렸다가 죽을 때까지 신원을 출력해야합니다. 그러나 키를 놓 자마자 식별자를 출력해야합니다. 키를 누를 때 다른 동작을 수행해서는 안되며 고유 식별자 외에는 아무것도 출력하지 않아야합니다.

답에 숫자 키패드에서 Tab, Pause, Enter, Enter, 숫자 Windows에서 왼쪽 Windows 키, 오른쪽 Windows 키, Insert 및 Ins와 같은 키 누름에 대한 코드 출력을 표시하십시오.

키보드가 매우 다른 경우 여전히 키보드의 모든 단일 키에 대해 다른 식별자를 출력해야합니다.


1
JS (브라우저 JS, 어쨌든)에서는 특정 키가 눌 렸는지 확인할 수 없습니다 (예 : Caps Lock, Num Lock, Scroll Lock, PrtScn). 이것은 JS가 대답 할 수 없다는 것을 의미합니까?
ETHproductions

2
@ETHproductions 실제로 그렇습니다. 어디서나 JS 애호가에게 사과드립니다.

2
5 개의 답변 후 수정 된 요구 사항이 제공됩니다 (지금 삭제 된 답변 포함). 정말 공평하지 않습니다 ...
Olivier Grégoire

6
Windows 키와 같은 많은 키보드에없는 키에 대한 출력을 요청하는 것이 공정하고 옳다고 생각하지 않습니다.
Notts90이 codidact.org에 있습니다.

1
@ Notts90 표준 미국 키보드 레이아웃의 일부가 아닙니까? upload.wikimedia.org/wikipedia/commons/thumb/5/51/…

답변:


22

x86 머신 코드, DOS 실행 파일, 29 * 28 바이트

FAE464D0E873FAE460D0E073F4D41005212192B402CD2188F2CD21EBE3

이것은 MS-DOSCOM 실행 파일 이며 IBM PC 호환 하드웨어 가 필요합니다 . 특히 8042 PS / 2 컨트롤러 또는 SMM 통한 컨트롤러 에뮬레이션 . 간단히 말해, 모든 주류 PC에서 즉시 사용할 수 있습니다.

소스 코드는

BITS 16

 ;Disable the interrupts so we don't compete with the IRQ 1 (the 8042 main
 ;device IRQ) handler (the ISR n. 9 by default) for the reading of the codes.
 cli

_wait:

 ;Is 'Output buffer full (OBF)' bit set?

 in al, 64h                ;Read the 8042 status register             
 shr al, 1                 ;Move bit 0 (OBF) into the carry flag

jnc _wait                  ;Keep spinning if CF = OBF not set

 ;Read the scan code S
 in al, 60h

 ;Is S a break code?

 shl al, 1                 ;Bit 7 is set if it is
jnc _wait

 ;PART 2

 ;AL = S mod 10h := y, AH = S / 10h := x
 aam 16
 add ax, 2121h             ;Make both quantities in the printable ASCII range (skip space though)

 ;Print y
 xchg dx, ax
 mov ah, 02h
 int 21h                   ;int 21/ah=02 prints the char in DL

 ;DH is still valid here, it holds x. We print it now
 mov dl, dh
 int 21h

 ;Never terminate
jmp _wait

프로그램을 두 부분으로 나누었습니다.

첫 번째 부분은 스캔 코드 읽기를 다룹니다 . 스캔 코드는 모든 키와 관련된 숫자 값입니다.
이들은 하드웨어 코드이며 OS 또는 문자셋에 의존하지 않습니다. 그것들은 키의 인코딩 된 쌍 (열, 행)과 같습니다.
모든 키에는 스캔 코드가 있으며 일부 키보드에서 볼 수있는 비표준 이상한 기능 키 (예 : "open calc"키)도 있습니다.
일부 키에는 멀티 바이트 스캔 코드가 있으며 바이트 시퀀스를 보면서 스트림을 결정 불가능하게하도록 설계된 접두사가 있습니다.
따라서 각 키는 고유 식별자, 심지어 CTRL, SHIFT, WinKeys 등을 얻습니다.

키를 놓을 때 전송 된 "중단 코드"만 처리되고 "코드 작성"은 무시됩니다.
전자는 더 높은 비트 (바이트의 경우 비트 7) 세트를 가지므로이를 쉽게 식별 할 수 있습니다.

두 번째 부분은 바이트 인쇄를 다룹니다.
인쇄는 항상 조립 시간이 길고 내장 기능이 없습니다.
키를 짧게 유지 하고 키 의 식별자 를 작성해야했기 때문에 개인 인코딩을 위해 10 진수 또는 16 진수를 버렸습니다.

바이트 xy. 여기서 x는 더 높은 니블이고 y는 더 낮은 문자는 다음과 같이 정의 된 두 개의 연속 문자 c 0 및 c 1 로 인쇄 됩니다.

c 0 = 0x21 + y
c 1 = 0x21 + x

하단 니블이 먼저 인쇄됩니다 (스왑이 절약 됨).
이론적 근거는 16 개의 가능한 니블 값 중 각각을 '!'의 연속 ASCII 문자로 매핑하는 것입니다.
간단히 이것은 16 진수이지만

  1. 니블 교환
  2. !"#$%&'()*+,-./01 대신 숫자 (als)로 0123456789abcdef

DOSBox 에서 실행 하고 임의의 키를 누르십시오 (일부는 특수 키이지만 Windows 프로세스에서는 DOSBox가 모든 키를 캡처 할 수는 없습니다)

DOSBox running the key identifier

이 프로그램은 종료되지 않습니다 (더 이상, 인터럽트를 비활성화하여 PC를 완전히 제어합니다).


* CodyGray 덕분에 감소 했습니다 .


IN명령을 사용하여 ROM BIOS 인터럽트를 호출하는 것 (예 : int 16h기능 10h) 보다 바이트 단위로 작게 작동 했습니까 ?
코디 그레이

@CodyGray 대부분의 경우 전체 루프를 건너 뛸 수 있습니다. 어떻게 든 나는 방금 in지시에 바로 뛰어 들었다 . 그것은 실제로 당신이 가진 아주 좋은 지적입니다. 아직 답변을 게시하지 않은 경우 답변으로 게시하지 않겠습니까? :)
마가렛 블룸

1
글쎄 지금 당신은 미친 이야기입니다! 기존 답변에 의견을 남기는 것보다 훨씬 많은 작업처럼 들립니다. :-p 무언가를 모아서 놀고 있습니다. 재미있는 팁 : 코드 골프를 할 때 xchg레지스터 중 하나 인 누산기가 1 바이트이므로 2 바이트보다 낫습니다 mov.
코디 그레이

1
문제 int 16h는 Shift 키, 스크롤 잠금 또는 일시 중지 / 중단 (아마도 다른 것)에 대한 스캔 코드를 얻지 못 하므로 문제 가 있다는 것입니다. I / O에서 직접 입력을 읽는 솔루션은 효과가 있지만 Ins / Del / Home / End / PgUp / PgDown 클러스터의 모든 키에 대해 동일한 값을 반환합니다.
코디 그레이

1
@PeterCordes : 또한 PAUSE에는 이상한 동작이 있습니다. IIUC는 키를 누를 때 make 코드와 함께 중단 코드를 보내고 키를 놓을 때 아무것도 보내지 않습니다. 또는 그것이 PC 게임 프로그래밍 백과 사전에서 내가 이해 한 것입니다.
ninjalj

12

Java 7 이상, 246228 바이트

import java.awt.event.*;class K{public static void main(String[]a){new java.awt.Frame(){{addKeyListener(new KeyAdapter(){public void keyPressed(KeyEvent e){System.out.println(e);}});show();setFocusTraversalKeysEnabled(0<0);}};}}

언 골프 드 :

import java.awt.event.*;
class K{
    static void main(String[]a){
        new java.awt.Frame(){
            {
                addKeyListener(new KeyAdapter(){
                    public void keyPressed(KeyEvent e){
                        System.out.println(e);
                    }
                });
                show();
                setFocusTraversalKeysEnabled(0<0);
            }
        };
    }
}

@ OlivierGrégoire에 대한 -18 덕분에 show(), 0<0그리고import java.awt.event.*;

결과 :

enter image description here

대문자 문자, 창 키, 캡 잠금 장치 등의 Shift-Press를 처리 할 수도 있습니다.

java.awt.event.KeyEvent[KEY_PRESSED,keyCode=27,keyText=Escape,keyChar=Escape,keyLocation=KEY_LOCATION_STANDARD,rawCode=27,primaryLevelUnicode=27,scancode=1,extendedKeyCode=0x1b] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=192,keyText=Back Quote,keyChar='`',keyLocation=KEY_LOCATION_STANDARD,rawCode=192,primaryLevelUnicode=96,scancode=41,extendedKeyCode=0xc0] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=9,keyText=Tab,keyChar=Tab,keyLocation=KEY_LOCATION_STANDARD,rawCode=9,primaryLevelUnicode=9,scancode=15,extendedKeyCode=0x9] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=20,keyText=Caps Lock,keyChar=Undefined keyChar,keyLocation=KEY_LOCATION_STANDARD,rawCode=20,primaryLevelUnicode=0,scancode=58,extendedKeyCode=0x14] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=16,keyText=Shift,keyChar=Undefined keyChar,modifiers=Shift,extModifiers=Shift,keyLocation=KEY_LOCATION_LEFT,rawCode=16,primaryLevelUnicode=0,scancode=42,extendedKeyCode=0x10] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=17,keyText=Ctrl,keyChar=Undefined keyChar,modifiers=Ctrl,extModifiers=Ctrl,keyLocation=KEY_LOCATION_LEFT,rawCode=17,primaryLevelUnicode=0,scancode=29,extendedKeyCode=0x11] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=524,keyText=Windows,keyChar=Undefined keyChar,keyLocation=KEY_LOCATION_LEFT,rawCode=91,primaryLevelUnicode=0,scancode=91,extendedKeyCode=0x20c] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=18,keyText=Alt,keyChar=Undefined keyChar,modifiers=Alt,extModifiers=Alt,keyLocation=KEY_LOCATION_LEFT,rawCode=18,primaryLevelUnicode=0,scancode=56,extendedKeyCode=0x12] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=32,keyText=Space,keyChar=' ',keyLocation=KEY_LOCATION_STANDARD,rawCode=32,primaryLevelUnicode=32,scancode=57,extendedKeyCode=0x20] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=18,keyText=Alt,keyChar=Undefined keyChar,modifiers=Alt,extModifiers=Alt,keyLocation=KEY_LOCATION_RIGHT,rawCode=18,primaryLevelUnicode=0,scancode=56,extendedKeyCode=0x12] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=17,keyText=Ctrl,keyChar=Undefined keyChar,modifiers=Ctrl,extModifiers=Ctrl,keyLocation=KEY_LOCATION_RIGHT,rawCode=17,primaryLevelUnicode=0,scancode=29,extendedKeyCode=0x11] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=37,keyText=Left,keyChar=Undefined keyChar,keyLocation=KEY_LOCATION_STANDARD,rawCode=37,primaryLevelUnicode=0,scancode=75,extendedKeyCode=0x25] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=16,keyText=Shift,keyChar=Undefined keyChar,modifiers=Shift,extModifiers=Shift,keyLocation=KEY_LOCATION_RIGHT,rawCode=16,primaryLevelUnicode=0,scancode=42,extendedKeyCode=0x10] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=38,keyText=Up,keyChar=Undefined keyChar,keyLocation=KEY_LOCATION_STANDARD,rawCode=38,primaryLevelUnicode=0,scancode=72,extendedKeyCode=0x26] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=39,keyText=Right,keyChar=Undefined keyChar,keyLocation=KEY_LOCATION_STANDARD,rawCode=39,primaryLevelUnicode=0,scancode=77,extendedKeyCode=0x27] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=96,keyText=NumPad-0,keyChar='0',keyLocation=KEY_LOCATION_NUMPAD,rawCode=96,primaryLevelUnicode=48,scancode=82,extendedKeyCode=0x60] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=110,keyText=NumPad .,keyChar='.',keyLocation=KEY_LOCATION_NUMPAD,rawCode=110,primaryLevelUnicode=46,scancode=83,extendedKeyCode=0x6e] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=10,keyText=Enter,keyChar=Enter,keyLocation=KEY_LOCATION_NUMPAD,rawCode=13,primaryLevelUnicode=13,scancode=28,extendedKeyCode=0xa] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=107,keyText=NumPad +,keyChar='+',keyLocation=KEY_LOCATION_NUMPAD,rawCode=107,primaryLevelUnicode=43,scancode=78,extendedKeyCode=0x6b] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=109,keyText=NumPad -,keyChar='-',keyLocation=KEY_LOCATION_NUMPAD,rawCode=109,primaryLevelUnicode=45,scancode=74,extendedKeyCode=0x6d] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=106,keyText=NumPad *,keyChar='*',keyLocation=KEY_LOCATION_NUMPAD,rawCode=106,primaryLevelUnicode=42,scancode=55,extendedKeyCode=0x6a] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=34,keyText=Page Down,keyChar=Undefined keyChar,keyLocation=KEY_LOCATION_STANDARD,rawCode=34,primaryLevelUnicode=0,scancode=81,extendedKeyCode=0x22] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=33,keyText=Page Up,keyChar=Undefined keyChar,keyLocation=KEY_LOCATION_STANDARD,rawCode=33,primaryLevelUnicode=0,scancode=73,extendedKeyCode=0x21] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=35,keyText=End,keyChar=Undefined keyChar,keyLocation=KEY_LOCATION_STANDARD,rawCode=35,primaryLevelUnicode=0,scancode=79,extendedKeyCode=0x23] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=36,keyText=Home,keyChar=Undefined keyChar,keyLocation=KEY_LOCATION_STANDARD,rawCode=36,primaryLevelUnicode=0,scancode=71,extendedKeyCode=0x24] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=127,keyText=Delete,keyChar=Delete,keyLocation=KEY_LOCATION_STANDARD,rawCode=46,primaryLevelUnicode=0,scancode=83,extendedKeyCode=0x7f] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=155,keyText=Insert,keyChar=Undefined keyChar,keyLocation=KEY_LOCATION_STANDARD,rawCode=45,primaryLevelUnicode=0,scancode=82,extendedKeyCode=0x9b] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=123,keyText=F12,keyChar=Undefined keyChar,keyLocation=KEY_LOCATION_STANDARD,rawCode=123,primaryLevelUnicode=0,scancode=88,extendedKeyCode=0x7b] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=122,keyText=F11,keyChar=Undefined keyChar,keyLocation=KEY_LOCATION_STANDARD,rawCode=122,primaryLevelUnicode=0,scancode=87,extendedKeyCode=0x7a] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=121,keyText=F10,keyChar=Undefined keyChar,keyLocation=KEY_LOCATION_STANDARD,rawCode=121,primaryLevelUnicode=0,scancode=68,extendedKeyCode=0x79] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=120,keyText=F9,keyChar=Undefined keyChar,keyLocation=KEY_LOCATION_STANDARD,rawCode=120,primaryLevelUnicode=0,scancode=67,extendedKeyCode=0x78] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=119,keyText=F8,keyChar=Undefined keyChar,keyLocation=KEY_LOCATION_STANDARD,rawCode=119,primaryLevelUnicode=0,scancode=66,extendedKeyCode=0x77] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=118,keyText=F7,keyChar=Undefined keyChar,keyLocation=KEY_LOCATION_STANDARD,rawCode=118,primaryLevelUnicode=0,scancode=65,extendedKeyCode=0x76] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=117,keyText=F6,keyChar=Undefined keyChar,keyLocation=KEY_LOCATION_STANDARD,rawCode=117,primaryLevelUnicode=0,scancode=64,extendedKeyCode=0x75] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=116,keyText=F5,keyChar=Undefined keyChar,keyLocation=KEY_LOCATION_STANDARD,rawCode=116,primaryLevelUnicode=0,scancode=63,extendedKeyCode=0x74] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=115,keyText=F4,keyChar=Undefined keyChar,keyLocation=KEY_LOCATION_STANDARD,rawCode=115,primaryLevelUnicode=0,scancode=62,extendedKeyCode=0x73] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=114,keyText=F3,keyChar=Undefined keyChar,keyLocation=KEY_LOCATION_STANDARD,rawCode=114,primaryLevelUnicode=0,scancode=61,extendedKeyCode=0x72] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=113,keyText=F2,keyChar=Undefined keyChar,keyLocation=KEY_LOCATION_STANDARD,rawCode=113,primaryLevelUnicode=0,scancode=60,extendedKeyCode=0x71] on frame0
java.awt.event.KeyEvent[KEY_PRESSED,keyCode=112,keyText=F1,keyChar=Undefined keyChar,keyLocation=KEY_LOCATION_STANDARD,rawCode=112,primaryLevelUnicode=0,scancode=59,extendedKeyCode=0x70] on frame0

의견은 긴 토론을위한 것이 아닙니다. 이 대화는 채팅 으로 이동 되었습니다 .
데니스

11

HTML (Javascript 포함), 46 31 자, 46 31 바이트

이것을 사용하여 숫자 키패드의 입력과 반환을 구별 하기 위해 LControl과 RControl ... apsiller가 signle 함수 호출로 수행 할 수있는 방법을 찾지 못했기 때문에 더 이상은 아닙니다.

<body onkeyup=alert(event.code)

특정 출력 :

이 숫자로 여전히 출력되는 출력물은 내가
키에 접근 할 수 있도록 랩탑에서 기다려야 할 수있는 것입니다.

PrtScn을 -> 캡쳐 PrintScreen
스크롤 잠금 -> ScrollLock이의
일시 정지 -> 일시 정지
왼쪽 Shift 키를 -> ShiftLeft
오른쪽 시프트를 -> ShiftRight은
Ctrl 키를 왼쪽 -> ContrlLeft
바로 Ctrl 키 -> CONTROLRIGHT가
Caps Lock 키 -> CapsLock 키
탭 -> 탭은
입력 -> 입력
수를 입력 pad-> NumpadEnter
Num Lock-> NumLock
삽입 -> 삽입
기능 숫자 패드 -> Numpad0
백 스페이스 -> 백 스페이스
델 -> 삭제
F1 ... F12 -> F12에 F1
Esc를 -> 탈출
왼쪽 윈도우 키를 -> MetaLeft의
권리 Windows 키-> MetaRight
Alt-> AltLeft AltGr-
> AltRight (버기의 종류, ControlLeft를 감지 한 다음 AltRight,그러나 실제로 AltRight입니다)
응용 프로그램 키 (컨텍스트 메뉴)-> ContextMenu

편집 : Fun'c 호출 후
1 바이트 절약 Lil 'Bits 및 ETHproduction 덕분에 18 바이트 절약, func 및 var 이름을 줄이는 것을 잊어 버렸습니다. RogerSpielker 덕분에 32 바이트가 절약되었습니다. 다시 -2 바이트 : -> 1 바이트 저장 : 마지막 슬래시 필요가 2 바이트 CraigAyre 덕분에 저장되지 : 기능을 2 바이트 ASCII 전용 덕분에 저장된 : 대신을 4 바이트 저장 우리가 텍스트를 가지고 있기 때문에, 필요가 없습니다, 에 대해 더 이상 기호 마감 : 1 바이트 ASCII 전용 (다시) 덕분에 저장되지 (모든 식별자이없는 고유 한) 내 대답의 상단에 말했듯이 15 바이트, apsillers 덕분에 저장된. ;

onkeydownonkeyup

with()
keywhich
'-'+>

<body onkeyup=alert(event.code)


잠깐만 ... 어떻게 ... Caps Lock ... 감지? 나는 그것이 불가능하다고 생각했다. PrtScn과 SysRq는 나를 위해 작동하지 않지만 Fn + End 및 Fn + Home을 사용하는 작은 키보드가있는 랩톱을 사용하고 있습니다.
ETHproductions

나는이 대답을 좋아하지만 문제가있는 것 같습니다. codepen.io/anon/pen/MoLPQM 에서 테스트 할 때 Tab은 아무것도보고하지 않습니다 . 또한 F12, PrtScn은이 규칙을 따르지 않습니다. "수신 한 키 누름으로 다른 작업을 수행해서는 안되며 고유 식별자와는 별도로 출력하지 않아야합니다."

HTML을 사용하는 @Lembik은 시스템이 키를 사용하는 것을 실제로 막을 수는 없습니다. 기계 (또는 시스템) 효과적인 언어 (예 : C)를 사용하여 키 입력을 인식하지 못하게해야합니다. 그리고 탭의 경우, 어떤 조건이 작동하는지 알 수 없습니다. (때로는 작동하지만 때로는 작동하지 않습니다. 내 대답이 통과 가능한 키를 처리하는 방법을 모르겠습니다.
V. Courtois

@Lembik 코드를 독립형 (스 니펫이나 바이올린 등이 아님), 전체 화면 페이지 (예 : F11 사용)로 보면 탭이 캡처됩니다. 탭을 캡처하지 않는다는 사실은 페이지에서 실행되는 코드가 아니라 더 큰 브라우저 환경 상태의 함수입니다. 기본 행동을 방지하기 위해 다음과 같이 <body onkeydown=return!!alert(event.code)>돌려 falsekeydown
보아야합니다

8

Tcl / Tk, 22 자

bind . <Key> {puts %K}

샘플 실행 :

Tcl / Tk로 식별 된 키

노트:

  • 에 대한 어떠한 권리도 Windows 키없는 내 키보드 ☹ ( 영리한 디자이너는 백라이트 스위치를 제자리에 놓습니다)
  • 숫자 패드의 삽입은 NumLock의 상태에 따라 다른 코드를 생성합니다
  • 볼륨 노브는 X.org 특정 코드를 생성하며 다른 코드는 모두 일반 키심입니다.

6

X.org를 사용한 배쉬, 21 바이트

xev|awk 'NR%2&&/\(k/'

불행히도 Linux의 MacBook에서 PrntScr, 숫자 키보드 및 모두가 아니므로 테스트 할 수 없습니다.

xev에서 마우스 및 키보드 이벤트를 출력하는 도구입니다 X.org. 나는 그것을 awk로 파이프하고 짝수 라인을 필터링하고 (키를 눌렀을 때 모든 키가 표시되므로 릴리스 할 때) 포함 된 (k문자열 만 선택하십시오 -이 문자열은 눌린 키를 설명하는 모든 줄에 있습니다.


질문에 나열된 예제 출력을 추가 할 수 있습니까?

1
종료 후 @Lembik의 모든 출력이 나타납니다.
enedil

아 그것은 스펙이 요구하는 것이 아닙니다. 나는 지금 그것을 정리할 것입니다.

이제 구문 오류가 발생합니다.

3
Linux는 X11을 의미하지 않습니다. 예를 들어 텍스트 콘솔 ( showkey -sP : P) 또는 순수한 Wayland GUI 데스크탑 에서는 작동하지 않습니다 . 이것은 실제로 bash + Xorg 답변입니다.
Peter Cordes

5

C 및 Win32, 240 224 216 205 202 194 191 바이트

#include<d3d.h>
#include<stdio.h>
w[9];p(x,y,a,b){printf("%X",a^b);}main(){w[1]=p;w[9]=p;CreateWindow(RegisterClass(w),0,1<<28,0,0,0,0,0,0,0,0);for(;GetMessage(w,0,16,0);)DispatchMessage(w);}

출력

TAB: F0008C00F0008

PAUSE: 450012C0450012

ENTER: 1C000CC01C000C

NUMPAD-ENTER: 11C000CC11C000C

WINDOWS-LEFT: 15B005AC15B005A

WINDOWS-RIGHT: 15C005DC15C005D

INSERT: 152002CC152002C

NUMPAD-INSERT: 52002CC052002C

설명

#include <d3d.h> // shortest built-in header that includes windows.h
#include <stdio.h> // for printf

w[9]; // space for wndclass-data array

// function castable to the signature of WNDPROC
p(x,y,a,b)
{
    // key and state are encoded in the last two 4-byte arguments to wndproc
    printf("%X",a^b);
}

main(m)
{
    // set minimal window class equivalent data pointing to wndproc above
    w[1]=p;w[9]=p;

    // create the window using the class, with WS_VISIBLE flag
    CreateWindow(RegisterClass(w),0,1<<28,0,0,0,0,0,0,0,0)
    for(;GetMessage(w,0,16,0);) // filter messages 15 and lower, which fire without input
        DispatchMessage(w);
}

편집

@ugoren에게 -16 감사합니다

-8 : 변경 WNDCLASSint 모든 멤버 10은 4 바이트이기 때문에 어레이

-11 : wndclass-data 배열의 부분 초기화, 9 개 요소로 감소

-3 : 암시 적 사용 int wndclass-data 배열에 decl

-8 : 출력 형식에서 개행을 제거합니다 (사양에 필요하지 않으며 printf 플러시없이 즉시 플러시). 이동 RegisterClassCreateWindow반환하여, 인수 ATOM; wndclass 이름을m유효한 문자열이되기 위해 0 바이트 만 필요한 .

-3 : 데이터에 wvar 재사용MSG


cout 을 사용하여 C ++에서 똑같은 일을하는 것은 그리 짧지 않을까요?
onurcanbektas

@Leth No. <iostream>+ std::cout<<a^b<<"\n"가 더 깁니다. 또한 함수 decls에 반환 유형을 추가해야한다고 m암시 할 수 없다고 생각합니다 int.
MooseBoys

와 함께 숯불 저장for(;GetMessage(&m,0,16,0);)DispatchMessage(&m);
ugoren

또한, p(x,y,a,b)(void*)p일부를 저장해야합니다.
ugoren

3

자바 (OpenJDK 8) , 369 바이트

import java.awt.event.*;import javax.swing.*;class F{public static void main(String[] a){JFrame f=new JFrame();f.addKeyListener(new KeyListener(){public void keyPressed(KeyEvent e){System.out.print(e.getKeyCode()*8+e.getKeyLocation());}public void keyTyped(KeyEvent e){}public void keyReleased(KeyEvent e){}});f.setVisible(true);f.setFocusTraversalKeysEnabled(false);}}

그래픽 인터페이스를 사용하기 때문에 TIO와 함께 실행할 수 없지만 내 컴퓨터에서는 작동합니다.

일시 중지 : 153
입력 : 81
숫자 키패드로 입력 : 84
왼쪽 슈퍼 키 : 193 (데스크톱의 메뉴 바로 가기를 비활성화 한 후)
오른쪽 슈퍼 키 : 201
삽입 : 241
Numpad에 삽입하십시오 : 522948 (하나는 없지만 Num lock이 꺼져있는 상태에서 5를 누르면 얻을 수 있습니다. Num lock이 켜져 있으면 812가됩니다.)

언 골프 / 설명 :

import java.awt.event.*; // KeyListener, KeyEvent
import javax.swing.*; // JFrame

class F implements KeyListener {

    public static void main(String[] a) {
        JFrame f=new JFrame(); // creates a new GUI frame
        f.addKeyListener(new KeyListener() {  // puts a KeyListener in the frame with the following properties:

            // Method that runs whenever a key is pressed
            public void keyPressed(KeyEvent e) {
                // getKeyCode returns an integer that uniquely identifies the key,
                // but not the location (e.g. LShift and RShift have the same key code)
                // To fix this, I scale up the key code by 8 and add the location,
                // which is always 0-4 (Standard, Left, Right, NumPad, or Unknown)
                // I could have scaled by 5 instead but I wasn't really thinking
                System.out.print(e.getKeyCode() * 8 + e.getKeyLocation());
                // If you want nicer-looking output, just change "print" to "println"
            }

            // Method that runs whenever a printable character is typed (does nothing)
            public void keyTyped(KeyEvent e){}

            // Method that runs whenever a keyboard key is released (does nothing)
            public void keyReleased(KeyEvent e){}
        });

        f.setVisible(true); // the frame will only except key presses if it is visible
        f.setFocusTraversalKeysEnabled(false); // disables "focus traversal" keys (such as Tab) from actually traversing focus
    }
}

탭 키에서 작동하는 것처럼 보이지 않습니까?
Poke

setFocusTraversalKeysEnabled(false);귀하의 답변 에이 문제가 해결됩니다.
매직 문어 Urn

@MagicOctopusUrn 나는 그것이 무엇을하는지 모르겠고 내가 원하는 것을 생각하지 않습니다 : P
musicman523

TAB 키에 대한 답변이 작동하므로 답변이 없으면 유효하지 않습니다.
매직 문어 Urn

Ohhhhh I see-Tab은 "포커스 traversal 키"입니다
musicman523

3

스칼라 2.10+, 279 자, 279 바이트

이제는 자바를하고있는 것처럼 느껴지더라도 스칼라 응답입니다. 어쨌든 우리는 TIO에서 테스트 할 수 없습니다.

import scala.swing._
import java.awt.event._
object M extends SimpleSwingApplication{def top=new MainFrame{this.peer.addKeyListener(new KeyListener(){def keyPressed(e:KeyEvent){print(e.getKeyCode+"-"+e.getKeyLocation)}
def keyReleased(e:KeyEvent){}
def keyTyped(e:KeyEvent){}})}}

상속되지 않은 메소드를 모두 사용하지 않더라도 모든 상속 된 메소드를 선언 해야하는 것은 슬픈 일입니다 .l 일부 컴파일러 플래그가 선언 할 수 없기 때문에 바이트 수에서 제거 할 수 있습니까?

이것은 (내 HTML-js 응답과 같이) keyPressed, "-"및 "location"을 인쇄합니다.

예를 들면 :

PrtScn-확인할 수없는
스크롤 잠금-> 145-1
일시 중지-> 19-1
왼쪽 Shift-> 16-2
오른쪽 Shift-> 16-3
왼쪽 Ctrl-> 17-2
오른쪽 Ctrl-> 17-3
Caps Lock- > 20-1
탭-> 확인할 수 없음 Enter-
> 10-1
숫자 키패드에서 입력-> 10-4
Num Lock-> 144-4
Insert-> 96-1
숫자 패드 입력-> 96-4
Backspace-> 8-1
델 -> 127-1
F1 ... F12 -> 112-1 123-1에
Esc를 -> 27-1은
Windows 키를 왼쪽 -> 524-2
바로 Windows 키 -> 524-3
Alt 키 -> 18 2
AltGr-> 18-3 (버기의 종류, 17-2를 감지 한 다음 18-3그러나 실제로 18-3)
응용 프로그램 키 (컨텍스트 메뉴)-> 525-1

나는 그것이 컴퓨터에 달려 있다고 생각하지만 : / 나는 지금 아제르바이잔 노트북을 사용하고 있습니다.


불필요한 선언을 계산하지 않으려면 비표준 컴파일러 플래그의 길이를 포함해야 할 수도 있습니다. 이전 컴파일러가 기본값으로 사용하지 않는 한? -std=c89최신 컴파일러는 기본적으로 c99 또는 c11이므로 C 답변은 일반적으로 컴파일 해야하지만 계산할 필요는 없습니다. 따라서 코드 골프 메타에서 판결이 무엇인지 잘 모르겠습니다.
Peter Cordes

3

TI-BASIC, 19 바이트

프로그램들

If Ans
Disp Ans
getKey
prgmS
  • 105를 입력하십시오.
  • 왼쪽 키 : 24,
  • 오른쪽 키 : 26,
  • Ins [ert]는 일반적으로 두 번의 키 누름이 필요하기 때문에 약간 다르지만 21 다음에 23이옵니다.

나머지 키는 다음과 같습니다.

여기에 이미지 설명을 입력하십시오

설명:

PROGRAM : S 편집기는 코드와 별도로 맨 위에 이름을 표시합니다. 이름은 "S"입니다

If Ans    // If the last input isn't zero
Disp Ans  // Display the last input
getKey    // Input a key press
prgmS     // Call the same program in a recursive fashion

불행히도 이것은 Arnold C에서 할 수 없으므로 TI-BASIC을 고수해야했습니다.


1
그 사진의 모든 키에서 작동합니까? 그렇지 않으면 어떤 키가 실패합니까?

2
예, 배터리에서 계산기를 꺼내지 않고 프로그램을 종료하기 위해 예약 된 on 버튼을 제외한 모든 키에 대해 작동합니다.
bearacuda13

@ bearacuda13 : 나는 18 년 전에 샀던 동등한 계산기를 가지고 있으며 수년간 ON 키 세부 사항을 알지 못했습니다. 나는 대학이 끝난 후 (11 년 전) 그것을 사용하고 있었지만, 누가 아는가?
sergiol

1

C #, 144 + 601 = 745 바이트

두 개의 클래스로 구성되어있어 하나의 클래스로 성공적으로 결합 할 수 없었습니다.

메인 클래스 :

namespace System.Windows.Forms{class P:Form{static void Main(){Application.Run(new P());}P(){new Reflection.M().U+=k=>Console.Write(k.f+k.v);}}}

훅 클래스 :

namespace System.Reflection{using Runtime.InteropServices;public class M{public delegate void d(s s);event d u;public event d U{add{if(h<1){j=m;h=SetWindowsHookEx(13,j,Marshal.GetHINSTANCE(Assembly.GetExecutingAssembly().GetModules()[0]),0);}u+=value;}remove{u-=value;}}public struct s{public int v;public int c;public int f;}[DllImport("user32.dll")]static extern int SetWindowsHookEx(int idHook,p lpfn,IntPtr hMod,int dwThreadId);delegate int p(int c,int w,IntPtr l);p j;int h;int m(int c,int w,IntPtr l){if(c>=0&u!=null&(w==257|w==261))u.Invoke((s)Marshal.PtrToStructure(l,typeof(s)));return -1;}}}

출력 :

  • 탭: 137
  • 중지: 147
  • 시작하다: 141
  • 숫자 패드 입력 : 142
  • 왼쪽 창 : 220
  • 올바른 Windows : 221
  • 끼워 넣다: 174
  • 숫자 패드 삽입 : 224

나는 변경하여 조금 아래로 바이트를 얻을 수 |||및 기타 유사한 골프를 친다 그러나 나의 뇌는 그 일을 한 후 휴식이 필요합니다!
TheLethalCoder

Hook 클래스에서는 다음과 public int v;public int c;public int f;같이 단축 될 수 있다고 생각 합니다.public int v,c,f;
Question Marks

@QuestionMarks 컴퓨터로 돌아 오면 좋은 아이디어가 나올 것입니다.
TheLethalCoder

1

오토 핫키 , 26 바이트

loop{
input,x,L1M
send %x%
}

테스트 할 수 없지만 (win-only) M옵션에

M : Control-A에서 Control-Z와 같은 수정 된 키 스트로크가 실제 ASCII 문자에 해당하는 경우 인식되고 전사됩니다.

그래서 잘해야합니다.


1

WinApi C ( gcc ), 156 바이트

#include <d3d.h>
#define b GetStdHandle(-10)
BYTE i[20];main(){SetConsoleMode(b,0);a:ReadConsoleInput(b,i,1,i+5);*i^1||*(i+4)||printf("%X\n",i[10]);goto a;}

이 프로그램 은 입력 한 각 키보드 키와 함께 Windows 가상 키 코드를 인쇄합니다 . \nprintf형식 문자열은 선택 사항입니다 (하지만 인간 친화적 출력한다)와 총 점수를 드롭 할 수있는 154 바이트 . taskmgr없이 프로그램을 쉽게 종료하는 방법은입니다 CTRL + PAUSE. Fn 키가있는 키보드가있는 경우이 프로그램은 Windows에서도 인식되지 않으므로 선택할 수 없습니다.

  • 어레이 의 #include <d3d.h>트릭과 영감에 대한 MooseBoys의 답변에 감사드립니다 BYTE.

로컬 변수, 가독성 및 컴파일러 경고가없는 프로그램은 다음과 같습니다.

#include <windows.h>
#include <stdio.h>

int main(void)
{
    HANDLE conIn = GetStdHandle(STD_INPUT_HANDLE);
    INPUT_RECORD ir;
    DWORD useless;

    SetConsoleMode(conIn, 0);

    for(;;)
    {
        ReadConsoleInput(conIn, &ir, 1, &useless);

        if(ir.EventType == KEY_EVENT && !ir.Event.KeyEvent.bKeyDown)
            printf("%X\n", ir.Event.KeyEvent.wVirtualKeyCode);
    }

    return 0;
}

1

C (gcc) + Win32, 94 95 98 105 107 110 바이트

#import"d3d.h"
j;f(){for(;;)for(j=191;j--;)GetAsyncKeyState(j)&(j<16||j>18)?printf("%d",j):0;}

이 코드는 포커스를 잃은 후에도 키를 캡처합니다.

printf("%d ",j);가독성을 높이기 위해 출력 사이에 공백 ( +1 바이트)을 추가하여 다음 스크린 샷이 기록 됩니다.

주요 스크린 샷

Left-ctrl Left-win Left-alt Space Right-alt Right-win Right-menu Right-ctrl Left-shift Z X C Right-shift Left-shift 1 2 3 Num 1 Num 2 Num 3 Left-shift +/= (on the main part) Num + Left-alt PrtScn

이 코드는 GetAsyncKeyState메시지 대기열을 확인하지 않고 키 상태를 쿼리 하는 데 사용 되며 일반적으로 다른 사용자 모드 접근 방식 (DirectInput 제외)보다 실시간입니다. 이 접근 방식은 키로거에서 널리 사용됩니다.

(j<16||j>18)일반 Ctrl / Alt / Shift를 필터링합니다. 16/17/18은 위치 지정 vkey 값과 함께 왼쪽 또는 오른쪽을 누를 때마다 트리거됩니다.


1

PowerShell, 34 바이트

$Host.UI.RawUI.ReadKey().Character

입력과 같은 줄에 출력하는 것은 다소 혼란 스러울 수 있습니다.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.