// Copyright 2014 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
(function () {
/**
* The possible states of the key.
* @const
* @type {Enum}
*/
var KEY_STATES = {
PRESSED: "pressed", // Key-down.
UNLOCKED: "unlocked", // Default state.
TAPPED: "tapped", // Key-down followed by key-up.
CHORDING: "chording", // Chording mode.
};
/**
* A map of the state of all modifier keys.
* @type {Object}
*/
var states = {};
Polymer('kb-modifier-key', {
up: function(event) {
if (this.state == KEY_STATES.PRESSED)
this.state = KEY_STATES.TAPPED;
else
this.state = KEY_STATES.UNLOCKED;
this.super([event]);
},
down: function(event) {
// First transition state so that populateDetails generates
// correct data.
switch (this.state) {
case KEY_STATES.UNLOCKED:
this.state = KEY_STATES.PRESSED;
break;
case KEY_STATES.TAPPED:
this.state = KEY_STATES.UNLOCKED;
break;
case KEY_STATES.PRESSED:
case KEY_STATES.CHORDING:
// We pressed another key at the same time,
// so ignore second press.
return;
default:
console.error("Undefined key state: " + state);
break;
}
this.super([event]);
},
/**
* Returns whether the modifier for this key is active.
* @return {boolean}
*/
isActive: function() {
return this.state != KEY_STATES.UNLOCKED;
},
/**
* Notifies key that a non-control keyed down.
* A control key is defined as one of shift, control or alt.
*/
onNonControlKeyDown: function() {
switch(this.state) {
case (KEY_STATES.PRESSED):
this.state = KEY_STATES.CHORDING;
break;
}
},
/**
* Notifies key that a non-control keyed was typed.
* A control key is defined as one of shift, control or alt.
*/
onNonControlKeyTyped: function() {
switch(this.state) {
case (KEY_STATES.TAPPED):
this.state = KEY_STATES.UNLOCKED;
break;
}
},
/**
* Called on a pointer-out event. Ends chording.
* @param {event} event The pointer-out event.
*/
out: function(event) {
// TODO(rsadam): Add chording event so that we don't reset
// when shift-chording.
if (this.state == KEY_STATES.CHORDING) {
this.state = KEY_STATES.UNLOCKED;
}
},
/*
* Overrides the autoRelease function to enable chording.
*/
autoRelease: function() {
},
populateDetails: function(caller) {
var detail = this.super([caller]);
if (this.state != KEY_STATES.UNLOCKED)
detail.activeModifier = this.charValue;
return detail;
},
/**
* Resets the modifier key state.
*/
reset: function() {
this.state = KEY_STATES.UNLOCKED;
},
get state() {
var key = this.charValue;
if (!key)
console.error("missing key for kb-modifier-key state: " + this);
// All keys default to the unlock state.
if (!(key in states))
states[key] = KEY_STATES.UNLOCKED;
return states[key];
},
set state(value) {
var key = this.charValue;
states[key] = value;
}
});
})();