<!DOCTYPE html>
<!--
@license
Copyright (C) 2016 The Android Open Source Project

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.
-->

<meta name="viewport" content="width=device-width, minimum-scale=1.0, initial-scale=1.0, user-scalable=yes">
<title>keyboard-shortcut-behavior</title>

<script src="../../bower_components/webcomponentsjs/webcomponents.min.js"></script>
<script src="../../bower_components/web-component-tester/browser.js"></script>
<link rel="import" href="../../test/common-test-setup.html"/>
<link rel="import" href="keyboard-shortcut-behavior.html">

<test-fixture id="basic">
  <template>
    <test-element></test-element>
  </template>
</test-fixture>

<test-fixture id="within-overlay">
  <template>
    <gr-overlay>
      <test-element></test-element>
    </gr-overlay>
  </template>
</test-fixture>

<script>
  suite('keyboard-shortcut-behavior tests', () => {
    const kb = window.Gerrit.KeyboardShortcutBinder;

    let element;
    let overlay;
    let sandbox;

    suiteSetup(() => {
      // Define a Polymer element that uses this behavior.
      Polymer({
        is: 'test-element',
        _legacyUndefinedCheck: true,
        behaviors: [Gerrit.KeyboardShortcutBehavior],
        keyBindings: {
          k: '_handleKey',
          enter: '_handleKey',
        },
        _handleKey() {},
      });
    });

    setup(() => {
      element = fixture('basic');
      overlay = fixture('within-overlay');
      sandbox = sinon.sandbox.create();
    });

    teardown(() => {
      sandbox.restore();
    });

    suite('ShortcutManager', () => {
      test('bindings management', () => {
        const mgr = new kb.ShortcutManager();
        const {NEXT_FILE} = kb.Shortcut;

        assert.isUndefined(mgr.getBindingsForShortcut(NEXT_FILE));
        mgr.bindShortcut(NEXT_FILE, ']', '}', 'right');
        assert.deepEqual(
            mgr.getBindingsForShortcut(NEXT_FILE),
            [']', '}', 'right']);
      });

      suite('binding descriptions', () => {
        function mapToObject(m) {
          const o = {};
          m.forEach((v, k) => o[k] = v);
          return o;
        }

        test('single combo description', () => {
          const mgr = new kb.ShortcutManager();
          assert.deepEqual(mgr.describeBinding('a'), ['a']);
          assert.deepEqual(mgr.describeBinding('a:keyup'), ['a']);
          assert.deepEqual(mgr.describeBinding('ctrl+a'), ['Ctrl', 'a']);
          assert.deepEqual(
              mgr.describeBinding('ctrl+shift+up:keyup'),
              ['Ctrl', 'Shift', '↑']);
        });

        test('combo set description', () => {
          const {GO_KEY, DOC_ONLY, ShortcutManager} = kb;
          const {GO_TO_OPENED_CHANGES, NEXT_FILE, PREV_FILE} = kb.Shortcut;

          const mgr = new ShortcutManager();
          assert.isNull(mgr.describeBindings(NEXT_FILE));

          mgr.bindShortcut(GO_TO_OPENED_CHANGES, GO_KEY, 'o');
          assert.deepEqual(
              mgr.describeBindings(GO_TO_OPENED_CHANGES),
              [['g', 'o']]);

          mgr.bindShortcut(NEXT_FILE, DOC_ONLY, ']', 'ctrl+shift+right:keyup');
          assert.deepEqual(
              mgr.describeBindings(NEXT_FILE),
              [[']'], ['Ctrl', 'Shift', '→']]);

          mgr.bindShortcut(PREV_FILE, '[');
          assert.deepEqual(mgr.describeBindings(PREV_FILE), [['[']]);
        });

        test('combo set description width', () => {
          const mgr = new kb.ShortcutManager();
          assert.strictEqual(mgr.comboSetDisplayWidth([['u']]), 1);
          assert.strictEqual(mgr.comboSetDisplayWidth([['g', 'o']]), 2);
          assert.strictEqual(mgr.comboSetDisplayWidth([['Shift', 'r']]), 6);
          assert.strictEqual(mgr.comboSetDisplayWidth([['x'], ['y']]), 4);
          assert.strictEqual(
              mgr.comboSetDisplayWidth([['x'], ['y'], ['Shift', 'z']]),
              12);
        });

        test('distribute shortcut help', () => {
          const mgr = new kb.ShortcutManager();
          assert.deepEqual(mgr.distributeBindingDesc([['o']]), [[['o']]]);
          assert.deepEqual(
              mgr.distributeBindingDesc([['g', 'o']]),
              [[['g', 'o']]]);
          assert.deepEqual(
              mgr.distributeBindingDesc([['ctrl', 'shift', 'meta', 'enter']]),
              [[['ctrl', 'shift', 'meta', 'enter']]]);
          assert.deepEqual(
              mgr.distributeBindingDesc([
                ['ctrl', 'shift', 'meta', 'enter'],
                ['o'],
              ]),
              [
                [['ctrl', 'shift', 'meta', 'enter']],
                [['o']],
              ]);
          assert.deepEqual(
              mgr.distributeBindingDesc([
                ['ctrl', 'enter'],
                ['meta', 'enter'],
                ['ctrl', 's'],
                ['meta', 's'],
              ]),
              [
                [['ctrl', 'enter'], ['meta', 'enter']],
                [['ctrl', 's'], ['meta', 's']],
              ]);
        });

        test('active shortcuts by section', () => {
          const {NEXT_FILE, NEXT_LINE, GO_TO_OPENED_CHANGES, SEARCH} =
              kb.Shortcut;
          const {DIFFS, EVERYWHERE, NAVIGATION} = kb.ShortcutSection;

          const mgr = new kb.ShortcutManager();
          mgr.bindShortcut(NEXT_FILE, ']');
          mgr.bindShortcut(NEXT_LINE, 'j');
          mgr.bindShortcut(GO_TO_OPENED_CHANGES, 'g+o');
          mgr.bindShortcut(SEARCH, '/');

          assert.deepEqual(
              mapToObject(mgr.activeShortcutsBySection()),
              {});

          mgr.attachHost({
            keyboardShortcuts() {
              return {
                [NEXT_FILE]: null,
              };
            },
          });
          assert.deepEqual(
              mapToObject(mgr.activeShortcutsBySection()),
              {
                [NAVIGATION]: [
                  {shortcut: NEXT_FILE, text: 'Select next file'},
                ],
              });

          mgr.attachHost({
            keyboardShortcuts() {
              return {
                [NEXT_LINE]: null,
              };
            },
          });
          assert.deepEqual(
              mapToObject(mgr.activeShortcutsBySection()),
              {
                [DIFFS]: [
                  {shortcut: NEXT_LINE, text: 'Go to next line'},
                ],
                [NAVIGATION]: [
                  {shortcut: NEXT_FILE, text: 'Select next file'},
                ],
              });

          mgr.attachHost({
            keyboardShortcuts() {
              return {
                [SEARCH]: null,
                [GO_TO_OPENED_CHANGES]: null,
              };
            },
          });
          assert.deepEqual(
              mapToObject(mgr.activeShortcutsBySection()),
              {
                [DIFFS]: [
                  {shortcut: NEXT_LINE, text: 'Go to next line'},
                ],
                [EVERYWHERE]: [
                  {shortcut: SEARCH, text: 'Search'},
                  {
                    shortcut: GO_TO_OPENED_CHANGES,
                    text: 'Go to Opened Changes',
                  },
                ],
                [NAVIGATION]: [
                  {shortcut: NEXT_FILE, text: 'Select next file'},
                ],
              });
        });

        test('directory view', () => {
          const {
              NEXT_FILE, NEXT_LINE, GO_TO_OPENED_CHANGES, SEARCH,
              SAVE_COMMENT,
          } = kb.Shortcut;
          const {DIFFS, EVERYWHERE, NAVIGATION} = kb.ShortcutSection;
          const {GO_KEY, ShortcutManager} = kb;

          const mgr = new ShortcutManager();
          mgr.bindShortcut(NEXT_FILE, ']');
          mgr.bindShortcut(NEXT_LINE, 'j');
          mgr.bindShortcut(GO_TO_OPENED_CHANGES, GO_KEY, 'o');
          mgr.bindShortcut(SEARCH, '/');
          mgr.bindShortcut(
              SAVE_COMMENT, 'ctrl+enter', 'meta+enter', 'ctrl+s', 'meta+s');

          assert.deepEqual(mapToObject(mgr.directoryView()), {});

          mgr.attachHost({
            keyboardShortcuts() {
              return {
                [GO_TO_OPENED_CHANGES]: null,
                [NEXT_FILE]: null,
                [NEXT_LINE]: null,
                [SAVE_COMMENT]: null,
                [SEARCH]: null,
              };
            },
          });
          assert.deepEqual(
              mapToObject(mgr.directoryView()),
              {
                [DIFFS]: [
                  {binding: [['j']], text: 'Go to next line'},
                  {
                    binding: [['Ctrl', 'Enter'], ['Meta', 'Enter']],
                    text: 'Save comment',
                  },
                  {
                    binding: [['Ctrl', 's'], ['Meta', 's']],
                    text: 'Save comment',
                  },
                ],
                [EVERYWHERE]: [
                  {binding: [['/']], text: 'Search'},
                  {binding: [['g', 'o']], text: 'Go to Opened Changes'},
                ],
                [NAVIGATION]: [
                  {binding: [[']']], text: 'Select next file'},
                ],
              });
        });
      });
    });

    test('doesn’t block kb shortcuts for non-whitelisted els', done => {
      const divEl = document.createElement('div');
      element.appendChild(divEl);
      element._handleKey = e => {
        assert.isFalse(element.shouldSuppressKeyboardShortcut(e));
        done();
      };
      MockInteractions.keyDownOn(divEl, 75, null, 'k');
    });

    test('blocks kb shortcuts for input els', done => {
      const inputEl = document.createElement('input');
      element.appendChild(inputEl);
      element._handleKey = e => {
        assert.isTrue(element.shouldSuppressKeyboardShortcut(e));
        done();
      };
      MockInteractions.keyDownOn(inputEl, 75, null, 'k');
    });

    test('blocks kb shortcuts for textarea els', done => {
      const textareaEl = document.createElement('textarea');
      element.appendChild(textareaEl);
      element._handleKey = e => {
        assert.isTrue(element.shouldSuppressKeyboardShortcut(e));
        done();
      };
      MockInteractions.keyDownOn(textareaEl, 75, null, 'k');
    });

    test('blocks kb shortcuts for anything in a gr-overlay', done => {
      const divEl = document.createElement('div');
      const element = overlay.querySelector('test-element');
      element.appendChild(divEl);
      element._handleKey = e => {
        assert.isTrue(element.shouldSuppressKeyboardShortcut(e));
        done();
      };
      MockInteractions.keyDownOn(divEl, 75, null, 'k');
    });

    test('blocks enter shortcut on an anchor', done => {
      const anchorEl = document.createElement('a');
      const element = overlay.querySelector('test-element');
      element.appendChild(anchorEl);
      element._handleKey = e => {
        assert.isTrue(element.shouldSuppressKeyboardShortcut(e));
        done();
      };
      MockInteractions.keyDownOn(anchorEl, 13, null, 'enter');
    });

    test('modifierPressed returns accurate values', () => {
      const spy = sandbox.spy(element, 'modifierPressed');
      element._handleKey = e => {
        element.modifierPressed(e);
      };
      MockInteractions.keyDownOn(element, 75, 'shift', 'k');
      assert.isTrue(spy.lastCall.returnValue);
      MockInteractions.keyDownOn(element, 75, null, 'k');
      assert.isFalse(spy.lastCall.returnValue);
      MockInteractions.keyDownOn(element, 75, 'ctrl', 'k');
      assert.isTrue(spy.lastCall.returnValue);
      MockInteractions.keyDownOn(element, 75, null, 'k');
      assert.isFalse(spy.lastCall.returnValue);
      MockInteractions.keyDownOn(element, 75, 'meta', 'k');
      assert.isTrue(spy.lastCall.returnValue);
      MockInteractions.keyDownOn(element, 75, null, 'k');
      assert.isFalse(spy.lastCall.returnValue);
      MockInteractions.keyDownOn(element, 75, 'alt', 'k');
      assert.isTrue(spy.lastCall.returnValue);
    });

    test('isModifierPressed returns accurate value', () => {
      const spy = sandbox.spy(element, 'isModifierPressed');
      element._handleKey = e => {
        element.isModifierPressed(e, 'shiftKey');
      };
      MockInteractions.keyDownOn(element, 75, 'shift', 'k');
      assert.isTrue(spy.lastCall.returnValue);
      MockInteractions.keyDownOn(element, 75, null, 'k');
      assert.isFalse(spy.lastCall.returnValue);
      MockInteractions.keyDownOn(element, 75, 'ctrl', 'k');
      assert.isFalse(spy.lastCall.returnValue);
      MockInteractions.keyDownOn(element, 75, null, 'k');
      assert.isFalse(spy.lastCall.returnValue);
      MockInteractions.keyDownOn(element, 75, 'meta', 'k');
      assert.isFalse(spy.lastCall.returnValue);
      MockInteractions.keyDownOn(element, 75, null, 'k');
      assert.isFalse(spy.lastCall.returnValue);
      MockInteractions.keyDownOn(element, 75, 'alt', 'k');
      assert.isFalse(spy.lastCall.returnValue);
    });

    suite('GO_KEY timing', () => {
      let handlerStub;

      setup(() => {
        element._shortcut_go_table.set('a', '_handleA');
        handlerStub = element._handleA = sinon.stub();
        sandbox.stub(Date, 'now').returns(10000);
      });

      test('success', () => {
        const e = {detail: {key: 'a'}, preventDefault: () => {}};
        sandbox.stub(element, 'shouldSuppressKeyboardShortcut').returns(false);
        element._shortcut_go_key_last_pressed = 9000;
        element._handleGoAction(e);
        assert.isTrue(handlerStub.calledOnce);
        assert.strictEqual(handlerStub.lastCall.args[0], e);
      });

      test('go key not pressed', () => {
        const e = {detail: {key: 'a'}, preventDefault: () => {}};
        sandbox.stub(element, 'shouldSuppressKeyboardShortcut').returns(false);
        element._shortcut_go_key_last_pressed = null;
        element._handleGoAction(e);
        assert.isFalse(handlerStub.called);
      });

      test('go key pressed too long ago', () => {
        const e = {detail: {key: 'a'}, preventDefault: () => {}};
        sandbox.stub(element, 'shouldSuppressKeyboardShortcut').returns(false);
        element._shortcut_go_key_last_pressed = 3000;
        element._handleGoAction(e);
        assert.isFalse(handlerStub.called);
      });

      test('should suppress', () => {
        const e = {detail: {key: 'a'}, preventDefault: () => {}};
        sandbox.stub(element, 'shouldSuppressKeyboardShortcut').returns(true);
        element._shortcut_go_key_last_pressed = 9000;
        element._handleGoAction(e);
        assert.isFalse(handlerStub.called);
      });

      test('unrecognized key', () => {
        const e = {detail: {key: 'f'}, preventDefault: () => {}};
        sandbox.stub(element, 'shouldSuppressKeyboardShortcut').returns(false);
        element._shortcut_go_key_last_pressed = 9000;
        element._handleGoAction(e);
        assert.isFalse(handlerStub.called);
      });
    });
  });
</script>
