blob: 3c2d980b307a91c61414b3e94de859878e001783 [file] [log] [blame]
Mike Frysinger598e8012022-09-07 08:38:34 -04001// Copyright 2022 The ChromiumOS Authors
Jason Linabad7562022-08-22 14:49:05 +10002// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5/**
6 * @fileoverview Unit tests for terminal_emulator.js.
7 */
8
9import {sleep} from './terminal_common.js';
Jason Lin5690e752022-08-30 15:36:45 +100010import {encodeKeyCombo, Modifier, XtermTerminal, XtermTerminalTestParams}
11 from './terminal_emulator.js';
12import {MockFunction, MockObject} from './terminal_test_mocks.js';
Jason Linabad7562022-08-22 14:49:05 +100013
14describe('terminal_emulator_tests.js', function() {
15 describe('XtermTerminal', function() {
16 beforeEach(async function() {
17 this.mocks = {
Jason Line9231bc2022-09-01 13:54:02 +100018 term: new MockObject({
19 options: {},
20 parser: {
21 registerOscHandler: () => {},
22 },
23 }),
Jason Linabad7562022-08-22 14:49:05 +100024 fontManager: new MockObject(),
Jason Lin2649da22022-10-12 10:16:44 +110025 xtermInternal: new MockObject({
26 getActualCellDimensions: () => ({width: 9, height: 22}),
27 }),
Jason Linabad7562022-08-22 14:49:05 +100028 };
29 const testParams = {};
30 for (const prop in this.mocks) {
31 testParams[prop] = this.mocks[prop].proxy;
32 }
33
34 this.terminal = new XtermTerminal({
35 storage: new lib.Storage.Memory(),
36 profileId: 'test',
37 enableWebGL: true,
38 testParams: /** @type {!XtermTerminalTestParams} */(testParams),
39 });
Jason Linc2504ae2022-09-02 13:03:31 +100040
41 // Some hacking because we don't run the decorate() function. Maybe we
42 // should just run it.
43 this.terminal.container_ = /** @type {!Element} */({
44 offsetWidth: 1000,
45 offsetHeight: 500,
46 });
Jason Lin8de3d282022-09-01 21:29:05 +100047 this.terminal.inited_ = true;
Jason Linabad7562022-08-22 14:49:05 +100048 });
49
50 describe('updateFont_()', function() {
51 it('updates font', async function() {
52 const updateFontPromise = this.terminal.updateFont_('font one');
53 assert.deepEqual(
54 await this.mocks.fontManager.whenCalled('loadFont'),
55 [['font one']]);
56 assert.equal(this.mocks.term.baseObj.options.fontFamily, undefined);
57 assert.isNotNull(this.terminal.pendingFont_);
Jason Linc2504ae2022-09-02 13:03:31 +100058 assert.equal(this.mocks.term.popMethodHistory('resize').length, 0);
Jason Linabad7562022-08-22 14:49:05 +100059
60 await updateFontPromise;
61 assert.equal(this.mocks.term.baseObj.options.fontFamily, 'font one');
62 assert.isNull(this.terminal.pendingFont_);
63 await sleep(0);
Jason Linc2504ae2022-09-02 13:03:31 +100064 assert.equal(this.mocks.term.popMethodHistory('resize').length, 1);
Jason Linabad7562022-08-22 14:49:05 +100065 });
66
67 it('refresh font when the font is the same', async function() {
68 this.mocks.term.baseObj.options.fontFamily = 'font one';
69 const updateFontPromise = this.terminal.updateFont_('font one');
70 assert.deepEqual(
71 await this.mocks.fontManager.whenCalled('loadFont'),
72 [['font one']]);
73 assert.equal(this.mocks.term.baseObj.options.fontFamily, 'font one');
74 assert.isNotNull(this.terminal.pendingFont_);
Jason Linc2504ae2022-09-02 13:03:31 +100075 assert.equal(this.mocks.term.popMethodHistory('resize').length, 0);
Jason Linabad7562022-08-22 14:49:05 +100076
77 await updateFontPromise;
78 // Note the extra space at the end.
79 assert.equal(this.mocks.term.baseObj.options.fontFamily, 'font one ');
80 assert.isNull(this.terminal.pendingFont_);
81 await sleep(0);
Jason Linc2504ae2022-09-02 13:03:31 +100082 assert.equal(this.mocks.term.popMethodHistory('resize').length, 1);
Jason Linabad7562022-08-22 14:49:05 +100083 });
84
85 it('aborts if pendingFont_ was changed', async function() {
86 const updateFontPromise = this.terminal.updateFont_('font one');
87 assert.deepEqual(
88 await this.mocks.fontManager.whenCalled('loadFont'),
89 [['font one']]);
90 assert.equal(this.mocks.term.baseObj.options.fontFamily, undefined);
91 assert.isNotNull(this.terminal.pendingFont_);
Jason Linc2504ae2022-09-02 13:03:31 +100092 assert.equal(this.mocks.term.popMethodHistory('resize').length, 0);
Jason Linabad7562022-08-22 14:49:05 +100093
94 this.terminal.pendingFont_ = 'font two';
95
96 await updateFontPromise;
97 assert.equal(this.mocks.term.baseObj.options.fontFamily, undefined);
98 assert.equal(this.terminal.pendingFont_, 'font two');
99 await sleep(0);
Jason Linc2504ae2022-09-02 13:03:31 +1000100 assert.equal(this.mocks.term.popMethodHistory('resize').length, 0);
Jason Linabad7562022-08-22 14:49:05 +1000101 });
102 });
Jason Lin5690e752022-08-30 15:36:45 +1000103
104 it('customKeyEventHandler_', async function() {
105 const mockHandler = new MockFunction();
106 const fakeEvent = {
107 type: 'keydown',
108 keyCode: 65,
109 ctrlKey: true,
110 };
111 this.terminal.keyDownHandlers_.set(encodeKeyCombo(Modifier.Ctrl, 65),
112 mockHandler.proxy);
113 assert.isFalse(this.terminal.customKeyEventHandler_(fakeEvent));
114 const history = mockHandler.popHistory();
115 assert.equal(history.length, 1);
116 assert.equal(history[0][0], fakeEvent);
117
118 assert.isFalse(this.terminal.customKeyEventHandler_({...fakeEvent,
119 type: 'keypress'}));
120 assert.isEmpty(mockHandler.popHistory());
121
122 assert.isTrue(this.terminal.customKeyEventHandler_({...fakeEvent,
123 shiftKey: true}));
124 assert.isEmpty(mockHandler.popHistory());
125
126 assert.isTrue(this.terminal.customKeyEventHandler_({...fakeEvent,
127 keyCode: 66}));
128 assert.isEmpty(mockHandler.popHistory());
129
130 assert.isTrue(this.terminal.customKeyEventHandler_({...fakeEvent,
131 ctrlKey: false}));
132 assert.isEmpty(mockHandler.popHistory());
133 });
Jason Linabad7562022-08-22 14:49:05 +1000134 });
135});