| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477 | 
							- <!DOCTYPE html>
 
- <html>
 
- <head>
 
-   <meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
 
-   <title>The source code</title>
 
-   <link href="../resources/prettify/prettify.css" type="text/css" rel="stylesheet" />
 
-   <script type="text/javascript" src="../resources/prettify/prettify.js"></script>
 
-   <style type="text/css">
 
-     .highlight { display: block; background-color: #ddd; }
 
-   </style>
 
-   <script type="text/javascript">
 
-     function highlight() {
 
-       document.getElementById(location.hash.replace(/#/, "")).className = "highlight";
 
-     }
 
-   </script>
 
- </head>
 
- <body onload="prettyPrint(); highlight();">
 
-   <pre class="prettyprint lang-js"><span id='Ext-util-KeyMap'>/**
 
- </span> * Handles mapping key events to handling functions for an element or a Component. One KeyMap can be used for multiple
 
-  * actions.
 
-  *
 
-  * A KeyMap must be configured with a {@link #target} as an event source which may be an Element or a Component.
 
-  *
 
-  * If the target is an element, then the `keydown` event will trigger the invocation of {@link #binding}s.
 
-  *
 
-  * It is possible to configure the KeyMap with a custom {@link #eventName} to listen for. This may be useful when the
 
-  * {@link #target} is a Component.
 
-  *
 
-  * The KeyMap's event handling requires that the first parameter passed is a key event. So if the Component's event
 
-  * signature is different, specify a {@link #processEvent} configuration which accepts the event's parameters and
 
-  * returns a key event.
 
-  *
 
-  * Functions specified in {@link #binding}s are called with this signature : `(String key, Ext.EventObject e)` (if the
 
-  * match is a multi-key combination the callback will still be called only once). A KeyMap can also handle a string
 
-  * representation of keys. By default KeyMap starts enabled.
 
-  *
 
-  * Usage:
 
-  *
 
-  *     // map one key by key code
 
-  *     var map = new Ext.util.KeyMap({
 
-  *         target: "my-element",
 
-  *         key: 13, // or Ext.EventObject.ENTER
 
-  *         fn: myHandler,
 
-  *         scope: myObject
 
-  *     });
 
-  *
 
-  *     // map multiple keys to one action by string
 
-  *     var map = new Ext.util.KeyMap({
 
-  *         target: "my-element",
 
-  *         key: "a\r\n\t",
 
-  *         fn: myHandler,
 
-  *         scope: myObject
 
-  *     });
 
-  *
 
-  *     // map multiple keys to multiple actions by strings and array of codes
 
-  *     var map = new Ext.util.KeyMap({
 
-  *         target: "my-element",
 
-  *         binding: [{
 
-  *             key: [10,13],
 
-  *             fn: function(){ alert("Return was pressed"); }
 
-  *         }, {
 
-  *             key: "abc",
 
-  *             fn: function(){ alert('a, b or c was pressed'); }
 
-  *         }, {
 
-  *             key: "\t",
 
-  *             ctrl:true,
 
-  *             shift:true,
 
-  *             fn: function(){ alert('Control + shift + tab was pressed.'); }
 
-  *         }]
 
-  *     });
 
-  *
 
-  * Since 4.1.0, KeyMaps can bind to Components and process key-based events fired by Components.
 
-  *
 
-  * To bind to a Component, use the single parameter form of constructor and include the Component event name
 
-  * to listen for, and a `processEvent` implementation which returns the key event for further processing by
 
-  * the KeyMap:
 
-  *
 
-  *     var map = new Ext.util.KeyMap({
 
-  *         target: myGridView,
 
-  *         eventName: 'itemkeydown',
 
-  *         processEvent: function(view, record, node, index, event) {
 
-  *
 
-  *             // Load the event with the extra information needed by the mappings
 
-  *             event.view = view;
 
-  *             event.store = view.getStore();
 
-  *             event.record = record;
 
-  *             event.index = index;
 
-  *             return event;
 
-  *         },
 
-  *         binding: {
 
-  *             key: Ext.EventObject.DELETE,
 
-  *             fn: function(keyCode, e) {
 
-  *                 e.store.remove(e.record);
 
-  *
 
-  *                 // Attempt to select the record that's now in its place
 
-  *                 e.view.getSelectionModel().select(e.index);
 
-  *                 e.view.el.focus();
 
-  *             }
 
-  *         }
 
-  *     });
 
-  */
 
- Ext.define('Ext.util.KeyMap', {
 
-     alternateClassName: 'Ext.KeyMap',
 
- <span id='Ext-util-KeyMap-cfg-target'>    /**
 
- </span>     * @cfg {Ext.Component/Ext.Element/HTMLElement/String} target
 
-      * The object on which to listen for the event specified by the {@link #eventName} config option.
 
-      */
 
- <span id='Ext-util-KeyMap-cfg-binding'>    /**
 
- </span>     * @cfg {Object/Object[][]} binding
 
-      * Either a single object describing a handling function for s specified key (or set of keys), or
 
-      * an array of such objects.
 
-      * @cfg {String/String[]} binding.key A single keycode or an array of keycodes to handle
 
-      * @cfg {Boolean}  binding.shift True to handle key only when shift is pressed, False to handle the
 
-      *  key only when shift is not pressed (defaults to undefined)
 
-      * @cfg {Boolean}  binding.ctrl True to handle key only when ctrl is pressed, False to handle the
 
-      *  key only when ctrl is not pressed (defaults to undefined)
 
-      * @cfg {Boolean}  binding.alt True to handle key only when alt is pressed, False to handle the key
 
-      *  only when alt is not pressed (defaults to undefined)
 
-      * @cfg {Function} binding.handler The function to call when KeyMap finds the expected key combination
 
-      * @cfg {Function} binding.fn Alias of handler (for backwards-compatibility)
 
-      * @cfg {Object}   binding.scope The scope of the callback function
 
-      * @cfg {String}   binding.defaultEventAction A default action to apply to the event. Possible values
 
-      *  are: stopEvent, stopPropagation, preventDefault. If no value is set no action is performed.
 
-      */
 
- <span id='Ext-util-KeyMap-cfg-processEventScope'>    /**
 
- </span>     * @cfg {Object} [processEventScope=this]
 
-      * The scope (`this` context) in which the {@link #processEvent} method is executed.
 
-      */
 
- <span id='Ext-util-KeyMap-cfg-ignoreInputFields'>    /**
 
- </span>     * @cfg {Boolean} [ignoreInputFields=false]
 
-      * Configure this as `true` if there are any input fields within the {@link #target}, and this KeyNav
 
-      * should not process events from input fields, (`&lt;input>, &lt;textarea> and elements with `contentEditable="true"`)
 
-      */
 
- <span id='Ext-util-KeyMap-cfg-eventName'>    /**
 
- </span>     * @cfg {String} eventName
 
-      * The event to listen for to pick up key events.
 
-      */
 
-     eventName: 'keydown',
 
-     constructor: function(config) {
 
-         var me = this;
 
-         // Handle legacy arg list in which the first argument is the target.
 
-         // TODO: Deprecate in V5
 
-         if ((arguments.length !== 1) || (typeof config === 'string') || config.dom || config.tagName || config === document || config.isComponent) {
 
-             me.legacyConstructor.apply(me, arguments);
 
-             return;
 
-         }
 
-         Ext.apply(me, config);
 
-         me.bindings = [];
 
-         if (!me.target.isComponent) {
 
-             me.target = Ext.get(me.target);
 
-         }
 
-         if (me.binding) {
 
-             me.addBinding(me.binding);
 
-         } else if (config.key) {
 
-             me.addBinding(config);
 
-         }
 
-         me.enable();
 
-     },
 
- <span id='Ext-util-KeyMap-method-legacyConstructor'>    /**
 
- </span>     * @private
 
-      * Old constructor signature
 
-      * @param {String/HTMLElement/Ext.Element/Ext.Component} el The element or its ID, or Component to bind to
 
-      * @param {Object} binding The binding (see {@link #addBinding})
 
-      * @param {String} [eventName="keydown"] The event to bind to
 
-      */
 
-     legacyConstructor: function(el, binding, eventName){
 
-         var me = this;
 
-         Ext.apply(me, {
 
-             target: Ext.get(el),
 
-             eventName: eventName || me.eventName,
 
-             bindings: []
 
-         });
 
-         if (binding) {
 
-             me.addBinding(binding);
 
-         }
 
-         me.enable();
 
-     },
 
- <span id='Ext-util-KeyMap-method-addBinding'>    /**
 
- </span>     * Add a new binding to this KeyMap.
 
-      *
 
-      * Usage:
 
-      *
 
-      *     // Create a KeyMap
 
-      *     var map = new Ext.util.KeyMap(document, {
 
-      *         key: Ext.EventObject.ENTER,
 
-      *         fn: handleKey,
 
-      *         scope: this
 
-      *     });
 
-      *
 
-      *     //Add a new binding to the existing KeyMap later
 
-      *     map.addBinding({
 
-      *         key: 'abc',
 
-      *         shift: true,
 
-      *         fn: handleKey,
 
-      *         scope: this
 
-      *     });
 
-      *
 
-      * @param {Object/Object[]} binding A single KeyMap config or an array of configs.
 
-      * The following config object properties are supported:
 
-      * @param {String/Array} binding.key A single keycode or an array of keycodes to handle.
 
-      * @param {Boolean} binding.shift True to handle key only when shift is pressed,
 
-      * False to handle the keyonly when shift is not pressed (defaults to undefined).
 
-      * @param {Boolean} binding.ctrl True to handle key only when ctrl is pressed,
 
-      * False to handle the key only when ctrl is not pressed (defaults to undefined).
 
-      * @param {Boolean} binding.alt True to handle key only when alt is pressed,
 
-      * False to handle the key only when alt is not pressed (defaults to undefined).
 
-      * @param {Function} binding.handler The function to call when KeyMap finds the
 
-      * expected key combination.
 
-      * @param {Function} binding.fn Alias of handler (for backwards-compatibility).
 
-      * @param {Object} binding.scope The scope of the callback function.
 
-      * @param {String} binding.defaultEventAction A default action to apply to the event.
 
-      * Possible values are: stopEvent, stopPropagation, preventDefault. If no value is
 
-      * set no action is performed..
 
-      */
 
-     addBinding : function(binding){
 
-         var keyCode = binding.key,
 
-             processed = false,
 
-             key,
 
-             keys,
 
-             keyString,
 
-             i,
 
-             len;
 
-         if (Ext.isArray(binding)) {
 
-             for (i = 0, len = binding.length; i < len; i++) {
 
-                 this.addBinding(binding[i]);
 
-             }
 
-             return;
 
-         }
 
-         if (Ext.isString(keyCode)) {
 
-             keys = [];
 
-             keyString = keyCode.toUpperCase();
 
-             for (i = 0, len = keyString.length; i < len; ++i){
 
-                 keys.push(keyString.charCodeAt(i));
 
-             }
 
-             keyCode = keys;
 
-             processed = true;
 
-         }
 
-         if (!Ext.isArray(keyCode)) {
 
-             keyCode = [keyCode];
 
-         }
 
-         if (!processed) {
 
-             for (i = 0, len = keyCode.length; i < len; ++i) {
 
-                 key = keyCode[i];
 
-                 if (Ext.isString(key)) {
 
-                     keyCode[i] = key.toUpperCase().charCodeAt(0);
 
-                 }
 
-             }
 
-         }
 
-         this.bindings.push(Ext.apply({
 
-             keyCode: keyCode
 
-         }, binding));
 
-     },
 
- <span id='Ext-util-KeyMap-method-handleTargetEvent'>    /**
 
- </span>     * Process the {@link #eventName event} from the {@link #target}.
 
-      * @private
 
-      * @param {Ext.EventObject} event
 
-      */
 
-     handleTargetEvent: (function() {
 
-         var tagRe = /input|textarea/i;
 
-         return function(event) {
 
-             var me = this,
 
-                 bindings, i, len,
 
-                 target, contentEditable;
 
-             if (this.enabled) { //just in case
 
-                 bindings = this.bindings;
 
-                 i = 0;
 
-                 len = bindings.length;
 
-                 // Process the event
 
-                 event = me.processEvent.apply(me||me.processEventScope, arguments);
 
-                 // Ignore events from input fields if configured to do so
 
-                 if (me.ignoreInputFields) {
 
-                     target = event.target;
 
-                     contentEditable = target.contentEditable;
 
-                     // contentEditable will default to inherit if not specified, only check if the
 
-                     // attribute has been set or explicitly set to true
 
-                     // http://html5doctor.com/the-contenteditable-attribute/
 
-                     if (tagRe.test(target.tagName) || (contentEditable === '' || contentEditable === 'true')) {
 
-                         return;
 
-                     }
 
-                 }
 
-                 // If the processor does not return a keyEvent, we can't process it.
 
-                 // Allow them to return false to cancel processing of the event
 
-                 if (!event.getKey) {
 
-                     return event;
 
-                 }
 
-                 for(; i < len; ++i){
 
-                     this.processBinding(bindings[i], event);
 
-                 }
 
-             }
 
-         }
 
-     }()),
 
- <span id='Ext-util-KeyMap-cfg-processEvent'>    /**
 
- </span>     * @cfg {Function} processEvent
 
-      * An optional event processor function which accepts the argument list provided by the
 
-      * {@link #eventName configured event} of the {@link #target}, and returns a keyEvent for processing by the KeyMap.
 
-      *
 
-      * This may be useful when the {@link #target} is a Component with s complex event signature, where the event is not
 
-      * the first parameter. Extra information from the event arguments may be injected into the event for use by the handler
 
-      * functions before returning it.
 
-      */
 
-     processEvent: function(event){
 
-         return event;
 
-     },
 
- <span id='Ext-util-KeyMap-method-processBinding'>    /**
 
- </span>     * Process a particular binding and fire the handler if necessary.
 
-      * @private
 
-      * @param {Object} binding The binding information
 
-      * @param {Ext.EventObject} event
 
-      */
 
-     processBinding: function(binding, event){
 
-         if (this.checkModifiers(binding, event)) {
 
-             var key = event.getKey(),
 
-                 handler = binding.fn || binding.handler,
 
-                 scope = binding.scope || this,
 
-                 keyCode = binding.keyCode,
 
-                 defaultEventAction = binding.defaultEventAction,
 
-                 i,
 
-                 len,
 
-                 keydownEvent = new Ext.EventObjectImpl(event);
 
-             for (i = 0, len = keyCode.length; i < len; ++i) {
 
-                 if (key === keyCode[i]) {
 
-                     if (handler.call(scope, key, event) !== true && defaultEventAction) {
 
-                         keydownEvent[defaultEventAction]();
 
-                     }
 
-                     break;
 
-                 }
 
-             }
 
-         }
 
-     },
 
- <span id='Ext-util-KeyMap-method-checkModifiers'>    /**
 
- </span>     * Check if the modifiers on the event match those on the binding
 
-      * @private
 
-      * @param {Object} binding
 
-      * @param {Ext.EventObject} event
 
-      * @return {Boolean} True if the event matches the binding
 
-      */
 
-     checkModifiers: function(binding, e) {
 
-         var keys = ['shift', 'ctrl', 'alt'],
 
-             i = 0,
 
-             len = keys.length,
 
-             val, key;
 
-         for (; i < len; ++i){
 
-             key = keys[i];
 
-             val = binding[key];
 
-             if (!(val === undefined || (val === e[key + 'Key']))) {
 
-                 return false;
 
-             }
 
-         }
 
-         return true;
 
-     },
 
- <span id='Ext-util-KeyMap-method-on'>    /**
 
- </span>     * Shorthand for adding a single key listener.
 
-      *
 
-      * @param {Number/Number[]/Object} key Either the numeric key code, array of key codes or an object with the
 
-      * following options: `{key: (number or array), shift: (true/false), ctrl: (true/false), alt: (true/false)}`
 
-      * @param {Function} fn The function to call
 
-      * @param {Object} [scope] The scope (`this` reference) in which the function is executed.
 
-      * Defaults to the browser window.
 
-      */
 
-     on: function(key, fn, scope) {
 
-         var keyCode, shift, ctrl, alt;
 
-         if (Ext.isObject(key) && !Ext.isArray(key)) {
 
-             keyCode = key.key;
 
-             shift = key.shift;
 
-             ctrl = key.ctrl;
 
-             alt = key.alt;
 
-         } else {
 
-             keyCode = key;
 
-         }
 
-         this.addBinding({
 
-             key: keyCode,
 
-             shift: shift,
 
-             ctrl: ctrl,
 
-             alt: alt,
 
-             fn: fn,
 
-             scope: scope
 
-         });
 
-     },
 
- <span id='Ext-util-KeyMap-method-isEnabled'>    /**
 
- </span>     * Returns true if this KeyMap is enabled
 
-      * @return {Boolean}
 
-      */
 
-     isEnabled : function() {
 
-         return this.enabled;
 
-     },
 
- <span id='Ext-util-KeyMap-method-enable'>    /**
 
- </span>     * Enables this KeyMap
 
-      */
 
-     enable: function() {
 
-         var me = this;
 
-         
 
-         if (!me.enabled) {
 
-             me.target.on(me.eventName, me.handleTargetEvent, me);
 
-             me.enabled = true;
 
-         }
 
-     },
 
- <span id='Ext-util-KeyMap-method-disable'>    /**
 
- </span>     * Disable this KeyMap
 
-      */
 
-     disable: function() {
 
-         var me = this;
 
-         
 
-         if (me.enabled) {
 
-             me.target.removeListener(me.eventName, me.handleTargetEvent, me);
 
-             me.enabled = false;
 
-         }
 
-     },
 
- <span id='Ext-util-KeyMap-method-setDisabled'>    /**
 
- </span>     * Convenience function for setting disabled/enabled by boolean.
 
-      * @param {Boolean} disabled
 
-      */
 
-     setDisabled : function(disabled) {
 
-         if (disabled) {
 
-             this.disable();
 
-         } else {
 
-             this.enable();
 
-         }
 
-     },
 
- <span id='Ext-util-KeyMap-method-destroy'>    /**
 
- </span>     * Destroys the KeyMap instance and removes all handlers.
 
-      * @param {Boolean} removeTarget True to also remove the {@link #target}
 
-      */
 
-     destroy: function(removeTarget) {
 
-         var me = this,
 
-             target = me.target;
 
-         me.bindings = [];
 
-         me.disable();
 
-         if (removeTarget === true) {
 
-             if (target.isComponent) {
 
-                 target.destroy();
 
-             } else {
 
-                 target.remove();
 
-             }
 
-         }
 
-         delete me.target;
 
-     }
 
- });</pre>
 
- </body>
 
- </html>
 
 
  |