From 88582726b7754211756d04fd66b11627e98b6d89 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?J=C3=B6rg=20Breitbart?= Date: Sun, 8 Mar 2020 20:08:22 +0100 Subject: [PATCH] implement SGR 21, sequence tests --- src/InputHandler.test.ts | 76 +++++++++++++++++++++++++++++++++++++++- src/InputHandler.ts | 13 +++---- 2 files changed, 82 insertions(+), 7 deletions(-) diff --git a/src/InputHandler.test.ts b/src/InputHandler.test.ts index de43022b1..3aeb4f8eb 100644 --- a/src/InputHandler.test.ts +++ b/src/InputHandler.test.ts @@ -10,7 +10,7 @@ import { Terminal } from './Terminal'; import { IBufferLine, IAttributeData } from 'common/Types'; import { DEFAULT_ATTR_DATA } from 'common/buffer/BufferLine'; import { CellData } from 'common/buffer/CellData'; -import { Attributes } from 'common/buffer/Constants'; +import { Attributes, UnderlineStyle } from 'common/buffer/Constants'; import { AttributeData } from 'common/buffer/AttributeData'; import { Params } from 'common/parser/Params'; import { MockCoreService, MockBufferService, MockDirtyRowService, MockOptionsService, MockLogService, MockCoreMouseService, MockCharsetService, MockUnicodeService } from 'common/TestUtils.test'; @@ -1445,4 +1445,78 @@ describe('InputHandler', () => { assert.deepEqual(getLines(term), ['¥¥ ¥¥', '¥¥ ¥', '¥¥ ¥', '¥¥¥¥¥', '']); }); }); + describe('extended SGR 4 support', () => { + let term: TestTerminal; + beforeEach(() => { + term = new TestTerminal({cols: 10, rows: 5}); + }); + it('4 | 24', () => { + term.writeSync('\x1b[4m'); + assert.equal(term.curAttrData.getUnderlineStyle(), UnderlineStyle.SINGLE); + term.writeSync('\x1b[24m'); + assert.equal(term.curAttrData.getUnderlineStyle(), UnderlineStyle.NONE); + }); + it('21 | 24', () => { + term.writeSync('\x1b[21m'); + assert.equal(term.curAttrData.getUnderlineStyle(), UnderlineStyle.DOUBLE); + term.writeSync('\x1b[24m'); + assert.equal(term.curAttrData.getUnderlineStyle(), UnderlineStyle.NONE); + }); + it('4:1 | 4:0', () => { + term.writeSync('\x1b[4:1m'); + assert.equal(term.curAttrData.getUnderlineStyle(), UnderlineStyle.SINGLE); + term.writeSync('\x1b[4:0m'); + assert.equal(term.curAttrData.getUnderlineStyle(), UnderlineStyle.NONE); + term.writeSync('\x1b[4:1m'); + assert.equal(term.curAttrData.getUnderlineStyle(), UnderlineStyle.SINGLE); + term.writeSync('\x1b[24m'); + assert.equal(term.curAttrData.getUnderlineStyle(), UnderlineStyle.NONE); + }); + it('4:2 | 4:0', () => { + term.writeSync('\x1b[4:2m'); + assert.equal(term.curAttrData.getUnderlineStyle(), UnderlineStyle.DOUBLE); + term.writeSync('\x1b[4:0m'); + assert.equal(term.curAttrData.getUnderlineStyle(), UnderlineStyle.NONE); + term.writeSync('\x1b[4:2m'); + assert.equal(term.curAttrData.getUnderlineStyle(), UnderlineStyle.DOUBLE); + term.writeSync('\x1b[24m'); + assert.equal(term.curAttrData.getUnderlineStyle(), UnderlineStyle.NONE); + }); + it('4:3 | 4:0', () => { + term.writeSync('\x1b[4:3m'); + assert.equal(term.curAttrData.getUnderlineStyle(), UnderlineStyle.CURLY); + term.writeSync('\x1b[4:0m'); + assert.equal(term.curAttrData.getUnderlineStyle(), UnderlineStyle.NONE); + term.writeSync('\x1b[4:3m'); + assert.equal(term.curAttrData.getUnderlineStyle(), UnderlineStyle.CURLY); + term.writeSync('\x1b[24m'); + assert.equal(term.curAttrData.getUnderlineStyle(), UnderlineStyle.NONE); + }); + it('4:4 | 4:0', () => { + term.writeSync('\x1b[4:4m'); + assert.equal(term.curAttrData.getUnderlineStyle(), UnderlineStyle.DOTTED); + term.writeSync('\x1b[4:0m'); + assert.equal(term.curAttrData.getUnderlineStyle(), UnderlineStyle.NONE); + term.writeSync('\x1b[4:4m'); + assert.equal(term.curAttrData.getUnderlineStyle(), UnderlineStyle.DOTTED); + term.writeSync('\x1b[24m'); + assert.equal(term.curAttrData.getUnderlineStyle(), UnderlineStyle.NONE); + }); + it('4:5 | 4:0', () => { + term.writeSync('\x1b[4:5m'); + assert.equal(term.curAttrData.getUnderlineStyle(), UnderlineStyle.DASHED); + term.writeSync('\x1b[4:0m'); + assert.equal(term.curAttrData.getUnderlineStyle(), UnderlineStyle.NONE); + term.writeSync('\x1b[4:5m'); + assert.equal(term.curAttrData.getUnderlineStyle(), UnderlineStyle.DASHED); + term.writeSync('\x1b[24m'); + assert.equal(term.curAttrData.getUnderlineStyle(), UnderlineStyle.NONE); + }); + it('4:x --> 4 should revert to single underline', () => { + term.writeSync('\x1b[4:5m'); + assert.equal(term.curAttrData.getUnderlineStyle(), UnderlineStyle.DASHED); + term.writeSync('\x1b[4m'); + assert.equal(term.curAttrData.getUnderlineStyle(), UnderlineStyle.SINGLE); + }); + }); }); diff --git a/src/InputHandler.ts b/src/InputHandler.ts index 1841f0110..3b35fddf4 100644 --- a/src/InputHandler.ts +++ b/src/InputHandler.ts @@ -14,7 +14,7 @@ import { StringToUtf32, stringFromCodePoint, utf32ToString, Utf8ToUtf32 } from ' import { DEFAULT_ATTR_DATA } from 'common/buffer/BufferLine'; import { EventEmitter, IEvent } from 'common/EventEmitter'; import { IParsingState, IDcsHandler, IEscapeSequenceParser, IParams, IFunctionIdentifier } from 'common/parser/Types'; -import { NULL_CELL_CODE, NULL_CELL_WIDTH, Attributes, FgFlags, BgFlags, Content } from 'common/buffer/Constants'; +import { NULL_CELL_CODE, NULL_CELL_WIDTH, Attributes, FgFlags, BgFlags, Content, UnderlineStyle } from 'common/buffer/Constants'; import { CellData } from 'common/buffer/CellData'; import { AttributeData } from 'common/buffer/AttributeData'; import { IAttributeData, IDisposable, IWindowOptions } from 'common/Types'; @@ -2107,17 +2107,17 @@ export class InputHandler extends Disposable implements IInputHandler { * 4:4 - dotted underline * 4:5 - dashed underline */ - private _processUnderline(subparams: Int32Array, attr: IAttributeData): void { + private _processUnderline(style: number, attr: IAttributeData): void { // treat extended attrs as immutable, thus always clone from old one // this is needed since the buffer only holds references to it attr.extended = attr.extended.clone(); - let style = subparams[0]; // default to 1 == single underline if (!~style || style > 5) { style = 1; } attr.extended.underlineStyle = style; + attr.fg |= FgFlags.UNDERLINE; // 0 deactivates underline if (style === 0) { @@ -2244,9 +2244,7 @@ export class InputHandler extends Disposable implements IInputHandler { } else if (p === 4) { // underlined text attr.fg |= FgFlags.UNDERLINE; - if (params.hasSubParams(i)) { - this._processUnderline(params.getSubParams(i), attr); - } + this._processUnderline(params.hasSubParams(i) ? params.getSubParams(i)[0] : UnderlineStyle.SINGLE, attr); } else if (p === 5) { // blink attr.fg |= FgFlags.BLINK; @@ -2260,6 +2258,9 @@ export class InputHandler extends Disposable implements IInputHandler { } else if (p === 2) { // dimmed text attr.bg |= BgFlags.DIM; + } else if (p === 21) { + // double underline + this._processUnderline(UnderlineStyle.DOUBLE, attr); } else if (p === 22) { // not bold nor faint attr.fg &= ~FgFlags.BOLD;