KeyboardEvent.key

この記事は翻訳が完了していません。 この記事の翻訳にご協力ください

KeyboardEvent インターフェイスの key はプロパティは読み取り専用で、ユーザーが押したキーの値を、 Shift キーなどの修飾キーやキーボードのロケールやレイアウトを考慮した値で返します。値は以下のように判断されます。

キーの値

キーの値の完全なリストを参照してください。

  • 押されたキーが印刷表現を持っている場合は、返された値は空ではない Unicode 文字の文字列で、キーの印刷表現が入ります。
  • 押されたキーが制御または特殊文字である場合は、返値は定義済みキー値の内の一つになります。
  • KeyboardEventデッドキーが押されたことを表すのであれば、キーの値は "Dead" になります。
  • キーボードの一部の特殊なキー (マルチメディアキーボードにおけるメディア制御のための拡張キーなど) は Windows のキーコードを生成しません。代わりに WM_APPCOMMAND イベントを起動します。これらのイベントは DOM キーボードイベントに対応付けられ、 Windows の「仮想キーコード」の中で、実際のキーコードではないものの紹介されます。
  • キーが特定できなかった場合は、 Unidentified の値を返します。

KeyboardEvent シーケンス

それぞれの KeyboardEvent はあらかじめ定められたシーケンスで発生します。キーが押された場合、発生する一連の KeyboardEventEvent.preventDefault が呼び出されないと想定すれば次のようになります。

  1. 最初に keydown イベントが発生します。キーがそれ以上押され続けてそのキーが文字を入力する場合は、イベントはプラットフォームの実装に依存した間隔で発生し続け、読み取り専用の KeyboardEvent.repeat プロパティが true に設定されます。
  2. もしキー入力が<input><textarea>もしくはHTMLElement.contentEditabletrue の要素に文字を挿入する場合は、 beforeinputinputイベント型がその順番で発火されます。 他の実装がkeypressイベントを実装していれば発火する可能性があることに注意してください。イベントはキーが押されている間連続で発火します。
  3. キーを離した際にkeyupイベントが発火します。これで一連の処理は終わりです。

1と3の処理で、 KeyboardEvent.key 属性が定義され、先ほど定義したルールにのっとって値が設定されます。

KeyboardEvent シーケンスの例

Consider the event sequence generated when we interact with the Shift and the 2 key using a U.S keyboard layout as compared to when we do so using a UK keyboard layout.

Try experimenting using the following two test cases:

  1. Press and hold the Shift key, then press 2 and release it. Next, release the Shift key.
  2. Press and hold the Shift key, then press and hold 2. Release the Shift key. Finally, release 2.

HTML

<div class="fx">
  <div>
    <textarea rows="5" name="test-target" id="test-target"></textarea>
    <button type="button" name="btn-clear-console" id="btn-clear-console">clear console</button>
  </div>
  <div class="flex">
    <pre id="console-log"></pre>
  </div>
</div>

CSS

.fx {
  -webkit-display: flex;
  display: flex;
  margin-left: -20px;
  margin-right: -20px;
}

.fx > div {
  padding-left: 20px;
  padding-right: 20px;
}

.fx > div:first-child {
   width: 30%;
}

.flex {
  -webkit-flex: 1;
  flex: 1;
}

#test-target {
  display: block;
  width: 100%;
  margin-bottom: 10px; 
}

JavaScript

let textarea = document.getElementById('test-target'),
consoleLog = document.getElementById('console-log'),
btnClearConsole = document.getElementById('btn-clear-console');

function logMessage(message) {
  document.getElementById("console-log").innerHTML += message + "<br>";
}

textarea.addEventListener('keydown', (e) => {
  if (!e.repeat)
    logMessage(`Key "${e.key}" pressed  [event: keydown]`);
  else
    logMessage(`Key "${e.key}" repeating  [event: keydown]`);
});

textarea.addEventListener('beforeinput', (e) => {
  logMessage(`Key "${e.data}" about to be input  [event: beforeinput]`);
});

textarea.addEventListener('input', (e) => {
  logMessage(`Key "${e.data}" input  [event: input]`);
});

textarea.addEventListener('keyup', (e) => {
  logMessage(`Key "${e.key}" released  [event: keyup]`);
});

btnClearConsole.addEventListener('click', (e) => {
  let child = consoleLog.firstChild;
  while (child) {
   consoleLog.removeChild(child);
   child = consoleLog.firstChild;
  }
});

結果

注: On browsers that don't fully implement the InputEvent interface which is used for the beforeinput and input events, you may get incorrect output on those lines of the log output.

Case 1

When the shift key is pressed, a keydown event is first fired, and the key property value is set to the string Shift. As we keep holding this key, the keydown event does not continue to fire repeatedly because it does not produce a character key.

When key 2 is pressed, another keydown event is fired for this new key press, and the key property value for the event is set to the string @ for the U.S keyboard type and " for the UK keyboard type, because of the active modifier shift key. The beforeinput and input events are fired next because a character key has been produced.

As we release the key 2, a keyup event is fired and the key property will maintain the string values @ and " for the different keyboard layouts respectively.

As we finally release the shift key, another keyup event is fired for it, and the key attribute value remains Shift.

Case 2

When the shift key is pressed, a keydown event is first fired, and the key property value is set to be the string Shift. As we keep holding this key, the keydown event does not continue to fire repeatedly because it produced no character key.

When key 2 is pressed, another keydown event is fired for this new key press, and the key property value for the event is set to be the string @ for the U.S keyboard type and " for the UK keyboard type, because of the active modifier shift key. The beforeinput and inputbeforeinput and input events are fired next because a character key has been produced. As we keep holding the key, the keydown event continues to fire repeatedly and the KeyboardEvent.repeat property is set to true. The beforeinput and input events are fired repeatedly as well.

As we release the shift key, a keyup event is fired for it, and the key attribute value remains Shift. At this point, notice that the key property value for the repeating keydown event of the key 2 key press is now "2" because the modifier shift key is no longer active. The same goes for the InputEvent.data property of the beforeinput and input events.

As we finally release the key 2, a keyup event is fired but the key property will be set to the string value 2 for both keyboard layouts because the modifier shift key is no longer active.

This example uses EventTarget.addEventListener() to listen for keydown events. When they occur, the key's value is checked to see if it's one of the keys the code is interested in, and if it is, it gets processed in some way (possibly by steering a spacecraft, perhaps by changing the selected cell in a spreadsheet).

window.addEventListener("keydown", function (event) {
  if (event.defaultPrevented) {
    return; // Do nothing if the event was already processed
  }

  switch (event.key) {
    case "Down": // IE/Edge specific value
    case "ArrowDown":
      // Do something for "down arrow" key press.
      break;
    case "Up": // IE/Edge specific value
    case "ArrowUp":
      // Do something for "up arrow" key press.
      break;
    case "Left": // IE/Edge specific value
    case "ArrowLeft":
      // Do something for "left arrow" key press.
      break;
    case "Right": // IE/Edge specific value
    case "ArrowRight":
      // Do something for "right arrow" key press.
      break;
    case "Enter":
      // Do something for "enter" or "return" key press.
      break;
    case "Esc": // IE/Edge specific value
    case "Escape":
      // Do something for "esc" key press.
      break;
    default:
      return; // Quit when this doesn't handle the key event.
  }

  // Cancel the default action to avoid it being handled twice
  event.preventDefault();
}, true);

仕様書

仕様書 状態 備考
UI Events
KeyboardEvent.key の定義
草案
Document Object Model (DOM) Level 3 Events Specification
KeyboardEvent.key の定義
廃止された 初回定義で、キーの値を含みます。

ブラウザーの互換性

Update compatibility data on GitHub
デスクトップモバイル
ChromeEdgeFirefoxInternet ExplorerOperaSafariAndroid webviewAndroid 版 ChromeAndroid 版 FirefoxAndroid 版 OperaiOSのSafariSamsung Internet
keyChrome 完全対応 51Edge 完全対応 12Firefox 完全対応 23IE 完全対応 9
補足
完全対応 9
補足
補足 IE's implementation does not completely match the current spec because it is based on an older version of the spec.
Opera 完全対応 38Safari 完全対応 10WebView Android 完全対応 51Chrome Android 完全対応 51Firefox Android 完全対応 23Opera Android 完全対応 41Safari iOS 完全対応 10Samsung Internet Android 完全対応 5.0
Dead keyChrome 完全対応 51Edge 完全対応 ≤79Firefox 未対応 なしIE 未対応 なしOpera 完全対応 38Safari ? WebView Android 完全対応 51Chrome Android 完全対応 51Firefox Android 未対応 なしOpera Android 完全対応 41Safari iOS ? Samsung Internet Android 完全対応 5.0
Non-printable keysChrome 完全対応 51Edge 完全対応 12Firefox 完全対応 23IE 完全対応 9
補足
完全対応 9
補足
補足 IE's implementation does not completely match the current spec because it is based on an older version of the spec.
Opera 完全対応 38Safari ? WebView Android 完全対応 51Chrome Android 完全対応 51Firefox Android 完全対応 23Opera Android 完全対応 41Safari iOS ? Samsung Internet Android 完全対応 5.0
Printable keysChrome 完全対応 51Edge 完全対応 12Firefox 完全対応 29IE 完全対応 9
補足
完全対応 9
補足
補足 IE's implementation does not completely match the current spec because it is based on an older version of the spec.
Opera 完全対応 38Safari ? WebView Android 完全対応 51Chrome Android 完全対応 51Firefox Android 完全対応 29Opera Android 完全対応 41Safari iOS ? Samsung Internet Android 完全対応 5.0

凡例

完全対応  
完全対応
未対応  
未対応
実装状況不明  
実装状況不明
実装ノートを参照してください。
実装ノートを参照してください。