diff --git a/static/third_party/js/keys.js b/static/third_party/js/keys.js
new file mode 100644
index 0000000..1f2a7ff
--- /dev/null
+++ b/static/third_party/js/keys.js
@@ -0,0 +1,192 @@
+/**
+ * Copyright 2008 Steve McKay.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/**
+ * Kibbles.Keys is a Javascript library providing simple cross browser
+ * keyboard event support.
+ */
+(function(){
+
+var _listening = false;
+
+// code to handler list map.
+// Wildcard listeners use magic code wildcards "before" and "after".
+var _listeners = {
+	before: [],
+	after: []
+};
+
+/*
+ * Map of key names to char code. This map is consulted before
+ * charCodeAt(0) is used to determine the character code.
+ *
+ * This map also serves as a definitive list of supported "special" keys.
+ * See _codeForEvent for details.
+ */
+var _CODE_MAP = {
+	ESC: 27,
+	ENTER: 13
+};
+
+/**
+ * Register a keypress listener.
+ */
+function _listen() {
+	if (_listening) return;
+
+	var d = document;
+	if (d.addEventListener) {
+		d.addEventListener('keypress', _handleKeyboardEvent, false);
+		d.addEventListener('keydown', _handleKeyDownEvent, false);
+	} else if (d.attachEvent) {
+		d.documentElement.attachEvent('onkeypress', _handleKeyboardEvent);
+		d.documentElement.attachEvent('onkeydown', _handleKeyDownEvent);
+	}
+	_listening = true;
+}
+
+/**
+ * Register a keypress listener for the supplied skip code.
+ */
+function _addKeyPressListener(spec, handler) {
+	var code = spec.toLowerCase();
+	if (code == "before" || code == "after") {
+		_listeners[code].push(handler);
+		return;
+	}
+
+	// try to find the character or key code.
+	code = _CODE_MAP[spec.toUpperCase()];
+	if (!code) {
+		code = spec.charCodeAt(0);
+	}
+	if (!_listeners[code]) {
+		_listeners[code] = [];
+	}
+	_listeners[code].push(handler);
+}
+
+/**
+ * Our handler for keypress events.
+ */
+function _handleKeyboardEvent(e) {
+
+	// If event is null, this is probably IE.
+	if (!e) e = window.event;
+
+	var source = _getSourceElement(e);
+	if (_isInputElement(source)) {
+		return;
+	}
+
+        if (_hasFlakeyModifier(e)) return;
+
+	var code = _codeForEvent(e);
+
+	if (code == undefined) return;
+
+	var payload = {
+		code: code
+	};
+
+	for (var i = 0; i < _listeners.before.length; i++) {
+		_listeners.before[i](payload);
+	}
+
+	var listeners = _listeners[code];
+	if (listeners) {
+		for (var i = 0; i < listeners.length; i++) {
+			listeners[i]({
+				code: code
+			});
+		}
+	}
+
+	for (var i = 0; i < _listeners.after.length; i++) {
+		_listeners.after[i](payload);
+	}
+}
+
+function _handleKeyDownEvent(e) {
+  if (!e) e = window.event;
+  var code = _codeForEvent(e);
+  if (code == _CODE_MAP['ESC'] || code == _CODE_MAP['ENTER']) {
+    _handleKeyboardEvent(e);
+  }
+}
+
+/**
+ * Returns the keycode associated with the event.
+ */
+function _codeForEvent(e) {
+  return e.keyCode ? e.keyCode : e.which;
+}
+
+/**
+ * Returns true if the supplied event has an associated modifier key
+ * that we have had trouble with in certain browsers.
+ */
+function _hasFlakeyModifier(e) {
+	return e.altKey || e.ctrlKey || e.metaKey;
+}
+
+/**
+ * Returns the source element for the supplied event.
+ */
+function _getSourceElement(e) {
+	var element = e.target;
+	if (!element) {
+		element = e.srcElement;
+	}
+
+	if (element.shadowRoot) {
+	  // Find the element within the shadowDOM.
+		const path = e.path || e.composedPath();
+	  element = path[0];
+	}
+
+	// If the source element is a text node, the parent is the object
+	// we're interested in.
+	if (element.nodeType == 3) {
+		element = element.parentNode;
+	}
+
+	return element;
+}
+
+/**
+ * Returns true if the element is a known form input element.
+ */
+function _isInputElement(element) {
+	return element.tagName == 'INPUT' || element.tagName == 'TEXTAREA';
+}
+
+/*
+ * A nice little namespace to call our own.
+ *
+ * Formalizing Kibbles.Keys as a traditional javascript class caused headaches
+ * with respect to capturing the context (what is "this" at any point in time).
+ * So we use a simple script exported via the "kibbles.keys" namespace.
+ */
+if (!window.kibbles)
+	window.kibbles = {}
+
+window.kibbles.keys = {
+	listen: _listen,
+	addKeyPressListener: _addKeyPressListener
+};
+
+})();
