IBufferLine interface

This commit is contained in:
Jörg Breitbart
2018-08-30 17:52:45 +02:00
parent 9a54cf639b
commit 59fc4af9a0
19 changed files with 116 additions and 108 deletions
+10 -10
View File
@@ -8,7 +8,7 @@ import { ITerminal } from './Types';
import { Buffer, DEFAULT_ATTR } from './Buffer'; import { Buffer, DEFAULT_ATTR } from './Buffer';
import { CircularList } from './common/CircularList'; import { CircularList } from './common/CircularList';
import { MockTerminal } from './utils/TestUtils.test'; import { MockTerminal } from './utils/TestUtils.test';
import { TerminalLine } from './TerminalLine'; import { BufferLine } from './TerminalLine';
const INIT_COLS = 80; const INIT_COLS = 80;
const INIT_ROWS = 24; const INIT_ROWS = 24;
@@ -37,7 +37,7 @@ describe('Buffer', () => {
describe('fillViewportRows', () => { describe('fillViewportRows', () => {
it('should fill the buffer with blank lines based on the size of the viewport', () => { it('should fill the buffer with blank lines based on the size of the viewport', () => {
const blankLineChar = TerminalLine.blankLine(terminal.cols, DEFAULT_ATTR).get(0); const blankLineChar = BufferLine.blankLine(terminal.cols, DEFAULT_ATTR).get(0);
buffer.fillViewportRows(); buffer.fillViewportRows();
assert.equal(buffer.lines.length, INIT_ROWS); assert.equal(buffer.lines.length, INIT_ROWS);
for (let y = 0; y < INIT_ROWS; y++) { for (let y = 0; y < INIT_ROWS; y++) {
@@ -180,7 +180,7 @@ describe('Buffer', () => {
buffer.fillViewportRows(); buffer.fillViewportRows();
// Create 10 extra blank lines // Create 10 extra blank lines
for (let i = 0; i < 10; i++) { for (let i = 0; i < 10; i++) {
buffer.lines.push(TerminalLine.blankLine(terminal.cols, DEFAULT_ATTR)); buffer.lines.push(BufferLine.blankLine(terminal.cols, DEFAULT_ATTR));
} }
// Set cursor to the bottom of the buffer // Set cursor to the bottom of the buffer
buffer.y = INIT_ROWS - 1; buffer.y = INIT_ROWS - 1;
@@ -200,7 +200,7 @@ describe('Buffer', () => {
buffer.fillViewportRows(); buffer.fillViewportRows();
// Create 10 extra blank lines // Create 10 extra blank lines
for (let i = 0; i < 10; i++) { for (let i = 0; i < 10; i++) {
buffer.lines.push(TerminalLine.blankLine(terminal.cols, DEFAULT_ATTR)); buffer.lines.push(BufferLine.blankLine(terminal.cols, DEFAULT_ATTR));
} }
// Set cursor to the bottom of the buffer // Set cursor to the bottom of the buffer
buffer.y = INIT_ROWS - 1; buffer.y = INIT_ROWS - 1;
@@ -273,7 +273,7 @@ describe('Buffer', () => {
describe ('translateBufferLineToString', () => { describe ('translateBufferLineToString', () => {
it('should handle selecting a section of ascii text', () => { it('should handle selecting a section of ascii text', () => {
const line = new TerminalLine(); const line = new BufferLine();
line.push([ null, 'a', 1, 'a'.charCodeAt(0)]); line.push([ null, 'a', 1, 'a'.charCodeAt(0)]);
line.push([ null, 'b', 1, 'b'.charCodeAt(0)]); line.push([ null, 'b', 1, 'b'.charCodeAt(0)]);
line.push([ null, 'c', 1, 'c'.charCodeAt(0)]); line.push([ null, 'c', 1, 'c'.charCodeAt(0)]);
@@ -285,7 +285,7 @@ describe('Buffer', () => {
}); });
it('should handle a cut-off double width character by including it', () => { it('should handle a cut-off double width character by including it', () => {
const line = new TerminalLine(); const line = new BufferLine();
line.push([ null, '語', 2, 35486 ]); line.push([ null, '語', 2, 35486 ]);
line.push([ null, '', 0, null]); line.push([ null, '', 0, null]);
line.push([ null, 'a', 1, 'a'.charCodeAt(0)]); line.push([ null, 'a', 1, 'a'.charCodeAt(0)]);
@@ -296,7 +296,7 @@ describe('Buffer', () => {
}); });
it('should handle a zero width character in the middle of the string by not including it', () => { it('should handle a zero width character in the middle of the string by not including it', () => {
const line = new TerminalLine(); const line = new BufferLine();
line.push([ null, '語', 2, '語'.charCodeAt(0) ]); line.push([ null, '語', 2, '語'.charCodeAt(0) ]);
line.push([ null, '', 0, null]); line.push([ null, '', 0, null]);
line.push([ null, 'a', 1, 'a'.charCodeAt(0)]); line.push([ null, 'a', 1, 'a'.charCodeAt(0)]);
@@ -313,7 +313,7 @@ describe('Buffer', () => {
}); });
it('should handle single width emojis', () => { it('should handle single width emojis', () => {
const line = new TerminalLine(); const line = new BufferLine();
line.push([ null, '😁', 1, '😁'.charCodeAt(0) ]); line.push([ null, '😁', 1, '😁'.charCodeAt(0) ]);
line.push([ null, 'a', 1, 'a'.charCodeAt(0)]); line.push([ null, 'a', 1, 'a'.charCodeAt(0)]);
buffer.lines.set(0, line); buffer.lines.set(0, line);
@@ -326,7 +326,7 @@ describe('Buffer', () => {
}); });
it('should handle double width emojis', () => { it('should handle double width emojis', () => {
const line = new TerminalLine(); const line = new BufferLine();
line.push([ null, '😁', 2, '😁'.charCodeAt(0) ]); line.push([ null, '😁', 2, '😁'.charCodeAt(0) ]);
line.push([ null, '', 0, null]); line.push([ null, '', 0, null]);
buffer.lines.set(0, line); buffer.lines.set(0, line);
@@ -337,7 +337,7 @@ describe('Buffer', () => {
const str2 = buffer.translateBufferLineToString(0, true, 0, 2); const str2 = buffer.translateBufferLineToString(0, true, 0, 2);
assert.equal(str2, '😁'); assert.equal(str2, '😁');
const line2 = new TerminalLine(); const line2 = new BufferLine();
line2.push([ null, '😁', 2, '😁'.charCodeAt(0) ]); line2.push([ null, '😁', 2, '😁'.charCodeAt(0) ]);
line2.push([ null, '', 0, null]); line2.push([ null, '', 0, null]);
line2.push([ null, 'a', 1, 'a'.charCodeAt(0)]); line2.push([ null, 'a', 1, 'a'.charCodeAt(0)]);
+6 -6
View File
@@ -4,10 +4,10 @@
*/ */
import { CircularList } from './common/CircularList'; import { CircularList } from './common/CircularList';
import { CharData, ITerminal, IBuffer } from './Types'; import { CharData, ITerminal, IBuffer, IBufferLine } from './Types';
import { EventEmitter } from './EventEmitter'; import { EventEmitter } from './EventEmitter';
import { IMarker } from 'xterm'; import { IMarker } from 'xterm';
import { TerminalLine } from './TerminalLine'; import { BufferLine } from './TerminalLine';
export const DEFAULT_ATTR = (0 << 18) | (257 << 9) | (256 << 0); export const DEFAULT_ATTR = (0 << 18) | (257 << 9) | (256 << 0);
export const CHAR_DATA_ATTR_INDEX = 0; export const CHAR_DATA_ATTR_INDEX = 0;
@@ -28,7 +28,7 @@ export const NULL_CELL_CODE = 32;
* - scroll position * - scroll position
*/ */
export class Buffer implements IBuffer { export class Buffer implements IBuffer {
public lines: CircularList<TerminalLine>; public lines: CircularList<IBufferLine>;
public ydisp: number; public ydisp: number;
public ybase: number; public ybase: number;
public y: number; public y: number;
@@ -85,7 +85,7 @@ export class Buffer implements IBuffer {
if (this.lines.length === 0) { if (this.lines.length === 0) {
let i = this._terminal.rows; let i = this._terminal.rows;
while (i--) { while (i--) {
this.lines.push(TerminalLine.blankLine(this._terminal.cols, DEFAULT_ATTR)); this.lines.push(BufferLine.blankLine(this._terminal.cols, DEFAULT_ATTR));
} }
} }
} }
@@ -98,7 +98,7 @@ export class Buffer implements IBuffer {
this.ybase = 0; this.ybase = 0;
this.y = 0; this.y = 0;
this.x = 0; this.x = 0;
this.lines = new CircularList<TerminalLine>(this._getCorrectBufferLength(this._terminal.rows)); this.lines = new CircularList<IBufferLine>(this._getCorrectBufferLength(this._terminal.rows));
this.scrollTop = 0; this.scrollTop = 0;
this.scrollBottom = this._terminal.rows - 1; this.scrollBottom = this._terminal.rows - 1;
this.setupTabStops(); this.setupTabStops();
@@ -147,7 +147,7 @@ export class Buffer implements IBuffer {
} else { } else {
// Add a blank line if there is no buffer left at the top to scroll to, or if there // Add a blank line if there is no buffer left at the top to scroll to, or if there
// are blank lines after the cursor // are blank lines after the cursor
this.lines.push(TerminalLine.blankLine(newCols, DEFAULT_ATTR)); this.lines.push(BufferLine.blankLine(newCols, DEFAULT_ATTR));
} }
} }
} }
+6 -6
View File
@@ -7,8 +7,8 @@ import { assert, expect } from 'chai';
import { InputHandler } from './InputHandler'; import { InputHandler } from './InputHandler';
import { MockInputHandlingTerminal } from './utils/TestUtils.test'; import { MockInputHandlingTerminal } from './utils/TestUtils.test';
import { NULL_CELL_CHAR, NULL_CELL_CODE, NULL_CELL_WIDTH, CHAR_DATA_CHAR_INDEX } from './Buffer'; import { NULL_CELL_CHAR, NULL_CELL_CODE, NULL_CELL_WIDTH, CHAR_DATA_CHAR_INDEX } from './Buffer';
import { TerminalLine } from './TerminalLine';
import { Terminal } from './Terminal'; import { Terminal } from './Terminal';
import { IBufferLine } from './Types';
describe('InputHandler', () => { describe('InputHandler', () => {
describe('save and restore cursor', () => { describe('save and restore cursor', () => {
@@ -90,7 +90,7 @@ describe('InputHandler', () => {
describe('regression tests', function(): void { describe('regression tests', function(): void {
type CharData = [number, string, number, number]; type CharData = [number, string, number, number];
function lineContent(line: TerminalLine): string { function lineContent(line: IBufferLine): string {
let content = ''; let content = '';
for (let i = 0; i < line.length; ++i) content += line.get(i)[CHAR_DATA_CHAR_INDEX]; for (let i = 0; i < line.length; ++i) content += line.get(i)[CHAR_DATA_CHAR_INDEX];
return content; return content;
@@ -128,8 +128,8 @@ describe('InputHandler', () => {
inputHandler.parse('1234567890'); inputHandler.parse('1234567890');
inputHandler.parse(Array(term.cols - 9).join('a')); inputHandler.parse(Array(term.cols - 9).join('a'));
inputHandler.parse('1234567890'); inputHandler.parse('1234567890');
const line1: TerminalLine = term.buffer.lines.get(0); // line for old variant const line1: IBufferLine = term.buffer.lines.get(0); // line for old variant
const line2: TerminalLine = term.buffer.lines.get(1); // line for new variant const line2: IBufferLine = term.buffer.lines.get(1); // line for new variant
expect(lineContent(line1)).equals(Array(term.cols - 9).join('a') + '1234567890'); expect(lineContent(line1)).equals(Array(term.cols - 9).join('a') + '1234567890');
expect(lineContent(line2)).equals(Array(term.cols - 9).join('a') + '1234567890'); expect(lineContent(line2)).equals(Array(term.cols - 9).join('a') + '1234567890');
@@ -205,8 +205,8 @@ describe('InputHandler', () => {
inputHandler.parse('1234567890'); inputHandler.parse('1234567890');
inputHandler.parse(Array(term.cols - 9).join('a')); inputHandler.parse(Array(term.cols - 9).join('a'));
inputHandler.parse('1234567890'); inputHandler.parse('1234567890');
const line1: TerminalLine = term.buffer.lines.get(0); // line for old variant const line1: IBufferLine = term.buffer.lines.get(0); // line for old variant
const line2: TerminalLine = term.buffer.lines.get(1); // line for new variant const line2: IBufferLine = term.buffer.lines.get(1); // line for new variant
expect(lineContent(line1)).equals(Array(term.cols - 9).join('a') + '1234567890'); expect(lineContent(line1)).equals(Array(term.cols - 9).join('a') + '1234567890');
expect(lineContent(line2)).equals(Array(term.cols - 9).join('a') + '1234567890'); expect(lineContent(line2)).equals(Array(term.cols - 9).join('a') + '1234567890');
+5 -5
View File
@@ -13,7 +13,7 @@ import { wcwidth } from './CharWidth';
import { EscapeSequenceParser } from './EscapeSequenceParser'; import { EscapeSequenceParser } from './EscapeSequenceParser';
import { ICharset } from './core/Types'; import { ICharset } from './core/Types';
import { Disposable } from './common/Lifecycle'; import { Disposable } from './common/Lifecycle';
import { TerminalLine } from './TerminalLine'; import { BufferLine } from './TerminalLine';
/** /**
* Map collect to glevel. Used in `selectCharset`. * Map collect to glevel. Used in `selectCharset`.
@@ -832,7 +832,7 @@ export class InputHandler extends Disposable implements IInputHandler {
// test: echo -e '\e[44m\e[1L\e[0m' // test: echo -e '\e[44m\e[1L\e[0m'
// blankLine(true) - xterm/linux behavior // blankLine(true) - xterm/linux behavior
buffer.lines.splice(scrollBottomAbsolute - 1, 1); buffer.lines.splice(scrollBottomAbsolute - 1, 1);
buffer.lines.splice(row, 0, TerminalLine.blankLine(this._terminal.cols, this._terminal.eraseAttr())); buffer.lines.splice(row, 0, BufferLine.blankLine(this._terminal.cols, this._terminal.eraseAttr()));
} }
// this.maxRange(); // this.maxRange();
@@ -862,7 +862,7 @@ export class InputHandler extends Disposable implements IInputHandler {
// test: echo -e '\e[44m\e[1M\e[0m' // test: echo -e '\e[44m\e[1M\e[0m'
// blankLine(true) - xterm/linux behavior // blankLine(true) - xterm/linux behavior
buffer.lines.splice(row, 1); buffer.lines.splice(row, 1);
buffer.lines.splice(j, 0, TerminalLine.blankLine(this._terminal.cols, this._terminal.eraseAttr())); buffer.lines.splice(j, 0, BufferLine.blankLine(this._terminal.cols, this._terminal.eraseAttr()));
} }
// this.maxRange(); // this.maxRange();
@@ -894,7 +894,7 @@ export class InputHandler extends Disposable implements IInputHandler {
while (param--) { while (param--) {
buffer.lines.splice(buffer.ybase + buffer.scrollTop, 1); buffer.lines.splice(buffer.ybase + buffer.scrollTop, 1);
buffer.lines.splice(buffer.ybase + buffer.scrollBottom, 0, TerminalLine.blankLine(this._terminal.cols, DEFAULT_ATTR)); buffer.lines.splice(buffer.ybase + buffer.scrollBottom, 0, BufferLine.blankLine(this._terminal.cols, DEFAULT_ATTR));
} }
// this.maxRange(); // this.maxRange();
this._terminal.updateRange(buffer.scrollTop); this._terminal.updateRange(buffer.scrollTop);
@@ -913,7 +913,7 @@ export class InputHandler extends Disposable implements IInputHandler {
while (param--) { while (param--) {
buffer.lines.splice(buffer.ybase + buffer.scrollBottom, 1); buffer.lines.splice(buffer.ybase + buffer.scrollBottom, 1);
buffer.lines.splice(buffer.ybase + buffer.scrollBottom, 0, TerminalLine.blankLine(this._terminal.cols, DEFAULT_ATTR)); buffer.lines.splice(buffer.ybase + buffer.scrollBottom, 0, BufferLine.blankLine(this._terminal.cols, DEFAULT_ATTR));
} }
// this.maxRange(); // this.maxRange();
this._terminal.updateRange(buffer.scrollTop); this._terminal.updateRange(buffer.scrollTop);
+5 -5
View File
@@ -5,11 +5,11 @@
import { assert } from 'chai'; import { assert } from 'chai';
import { IMouseZoneManager, IMouseZone } from './ui/Types'; import { IMouseZoneManager, IMouseZone } from './ui/Types';
import { ILinkMatcher, ITerminal } from './Types'; import { ILinkMatcher, ITerminal, IBufferLine } from './Types';
import { Linkifier } from './Linkifier'; import { Linkifier } from './Linkifier';
import { MockBuffer, MockTerminal } from './utils/TestUtils.test'; import { MockBuffer, MockTerminal } from './utils/TestUtils.test';
import { CircularList } from './common/CircularList'; import { CircularList } from './common/CircularList';
import { TerminalLine } from './TerminalLine'; import { BufferLine } from './TerminalLine';
class TestLinkifier extends Linkifier { class TestLinkifier extends Linkifier {
constructor(terminal: ITerminal) { constructor(terminal: ITerminal) {
@@ -43,14 +43,14 @@ describe('Linkifier', () => {
terminal = new MockTerminal(); terminal = new MockTerminal();
terminal.cols = 100; terminal.cols = 100;
terminal.buffer = new MockBuffer(); terminal.buffer = new MockBuffer();
(<MockBuffer>terminal.buffer).setLines(new CircularList<TerminalLine>(20)); (<MockBuffer>terminal.buffer).setLines(new CircularList<IBufferLine>(20));
terminal.buffer.ydisp = 0; terminal.buffer.ydisp = 0;
linkifier = new TestLinkifier(terminal); linkifier = new TestLinkifier(terminal);
mouseZoneManager = new TestMouseZoneManager(); mouseZoneManager = new TestMouseZoneManager();
}); });
function stringToRow(text: string): TerminalLine { function stringToRow(text: string): IBufferLine {
const result = new TerminalLine(); const result = new BufferLine();
for (let i = 0; i < text.length; i++) { for (let i = 0; i < text.length; i++) {
result.push([0, text.charAt(i), 1, text.charCodeAt(i)]); result.push([0, text.charAt(i), 1, text.charCodeAt(i)]);
} }
+2 -3
View File
@@ -4,10 +4,9 @@
*/ */
import { IMouseZoneManager } from './ui/Types'; import { IMouseZoneManager } from './ui/Types';
import { ILinkHoverEvent, ILinkMatcher, LinkMatcherHandler, LinkHoverEventTypes, ILinkMatcherOptions, ILinkifier, ITerminal } from './Types'; import { ILinkHoverEvent, ILinkMatcher, LinkMatcherHandler, LinkHoverEventTypes, ILinkMatcherOptions, ILinkifier, ITerminal, IBufferLine } from './Types';
import { MouseZone } from './ui/MouseZoneManager'; import { MouseZone } from './ui/MouseZoneManager';
import { EventEmitter } from './EventEmitter'; import { EventEmitter } from './EventEmitter';
import { TerminalLine } from './TerminalLine';
import { CHAR_DATA_ATTR_INDEX } from './Buffer'; import { CHAR_DATA_ATTR_INDEX } from './Buffer';
/** /**
@@ -171,7 +170,7 @@ export class Linkifier extends EventEmitter implements ILinkifier {
return; return;
} }
// If the first row is wrapped, backtrack to find the origin row and linkify that // If the first row is wrapped, backtrack to find the origin row and linkify that
let line: TerminalLine; let line: IBufferLine;
do { do {
rowIndex--; rowIndex--;
+7 -7
View File
@@ -8,9 +8,9 @@ import { CharMeasure } from './ui/CharMeasure';
import { SelectionManager, SelectionMode } from './SelectionManager'; import { SelectionManager, SelectionMode } from './SelectionManager';
import { SelectionModel } from './SelectionModel'; import { SelectionModel } from './SelectionModel';
import { BufferSet } from './BufferSet'; import { BufferSet } from './BufferSet';
import { ITerminal, IBuffer } from './Types'; import { ITerminal, IBuffer, IBufferLine } from './Types';
import { MockTerminal } from './utils/TestUtils.test'; import { MockTerminal } from './utils/TestUtils.test';
import { TerminalLine } from './TerminalLine'; import { BufferLine } from './TerminalLine';
class TestMockTerminal extends MockTerminal { class TestMockTerminal extends MockTerminal {
emit(event: string, data: any): void {} emit(event: string, data: any): void {}
@@ -53,16 +53,16 @@ describe('SelectionManager', () => {
selectionManager = new TestSelectionManager(terminal, null); selectionManager = new TestSelectionManager(terminal, null);
}); });
function stringToRow(text: string): TerminalLine { function stringToRow(text: string): IBufferLine {
const result = new TerminalLine(); const result = new BufferLine();
for (let i = 0; i < text.length; i++) { for (let i = 0; i < text.length; i++) {
result.push([0, text.charAt(i), 1, text.charCodeAt(i)]); result.push([0, text.charAt(i), 1, text.charCodeAt(i)]);
} }
return result; return result;
} }
function stringArrayToRow(chars: string[]): TerminalLine { function stringArrayToRow(chars: string[]): IBufferLine {
const line = new TerminalLine(); const line = new BufferLine();
chars.map(c => line.push([0, c, 1, c.charCodeAt(0)])); chars.map(c => line.push([0, c, 1, c.charCodeAt(0)]));
return line; return line;
} }
@@ -100,7 +100,7 @@ describe('SelectionManager', () => {
}); });
it('should expand selection for wide characters', () => { it('should expand selection for wide characters', () => {
// Wide characters use a special format // Wide characters use a special format
const line = new TerminalLine(); const line = new BufferLine();
const data: [number, string, number, number][] = [ const data: [number, string, number, number][] = [
[null, '中', 2, '中'.charCodeAt(0)], [null, '中', 2, '中'.charCodeAt(0)],
[null, '', 0, null], [null, '', 0, null],
+2 -3
View File
@@ -3,7 +3,7 @@
* @license MIT * @license MIT
*/ */
import { ITerminal, ISelectionManager, IBuffer, CharData, XtermListener } from './Types'; import { ITerminal, ISelectionManager, IBuffer, CharData, XtermListener, IBufferLine } from './Types';
import { MouseHelper } from './utils/MouseHelper'; import { MouseHelper } from './utils/MouseHelper';
import * as Browser from './shared/utils/Browser'; import * as Browser from './shared/utils/Browser';
import { CharMeasure } from './ui/CharMeasure'; import { CharMeasure } from './ui/CharMeasure';
@@ -11,7 +11,6 @@ import { EventEmitter } from './EventEmitter';
import { SelectionModel } from './SelectionModel'; import { SelectionModel } from './SelectionModel';
import { CHAR_DATA_WIDTH_INDEX, CHAR_DATA_CHAR_INDEX, CHAR_DATA_CODE_INDEX } from './Buffer'; import { CHAR_DATA_WIDTH_INDEX, CHAR_DATA_CHAR_INDEX, CHAR_DATA_CODE_INDEX } from './Buffer';
import { AltClickHandler } from './handlers/AltClickHandler'; import { AltClickHandler } from './handlers/AltClickHandler';
import { TerminalLine } from './TerminalLine';
/** /**
* The number of pixels the mouse needs to be above or below the viewport in * The number of pixels the mouse needs to be above or below the viewport in
@@ -662,7 +661,7 @@ export class SelectionManager extends EventEmitter implements ISelectionManager
* latter takes into account wide characters. * latter takes into account wide characters.
* @param coords The coordinates to find the 2 index for. * @param coords The coordinates to find the 2 index for.
*/ */
private _convertViewportColToCharacterIndex(bufferLine: TerminalLine, coords: [number, number]): number { private _convertViewportColToCharacterIndex(bufferLine: IBufferLine, coords: [number, number]): number {
let charIndex = coords[0]; let charIndex = coords[0];
for (let i = 0; coords[0] >= i; i++) { for (let i = 0; coords[0] >= i; i++) {
const char = bufferLine.get(i); const char = bufferLine.get(i);
+4 -4
View File
@@ -7,7 +7,7 @@ import { assert, expect } from 'chai';
import { Terminal } from './Terminal'; import { Terminal } from './Terminal';
import { MockViewport, MockCompositionHelper, MockRenderer } from './utils/TestUtils.test'; import { MockViewport, MockCompositionHelper, MockRenderer } from './utils/TestUtils.test';
import { CHAR_DATA_CHAR_INDEX, CHAR_DATA_WIDTH_INDEX, DEFAULT_ATTR } from './Buffer'; import { CHAR_DATA_CHAR_INDEX, CHAR_DATA_WIDTH_INDEX, DEFAULT_ATTR } from './Buffer';
import { TerminalLine } from './TerminalLine'; import { BufferLine } from './TerminalLine';
const INIT_COLS = 80; const INIT_COLS = 80;
const INIT_ROWS = 24; const INIT_ROWS = 24;
@@ -142,7 +142,7 @@ describe('term.js addons', () => {
assert.equal(term.buffer.lines.length, term.rows); assert.equal(term.buffer.lines.length, term.rows);
assert.deepEqual(term.buffer.lines.get(0), promptLine); assert.deepEqual(term.buffer.lines.get(0), promptLine);
for (let i = 1; i < term.rows; i++) { for (let i = 1; i < term.rows; i++) {
assert.deepEqual(term.buffer.lines.get(i), TerminalLine.blankLine(term.cols, DEFAULT_ATTR)); assert.deepEqual(term.buffer.lines.get(i), BufferLine.blankLine(term.cols, DEFAULT_ATTR));
} }
}); });
it('should clear a buffer larger than rows', () => { it('should clear a buffer larger than rows', () => {
@@ -159,7 +159,7 @@ describe('term.js addons', () => {
assert.equal(term.buffer.lines.length, term.rows); assert.equal(term.buffer.lines.length, term.rows);
assert.deepEqual(term.buffer.lines.get(0), promptLine); assert.deepEqual(term.buffer.lines.get(0), promptLine);
for (let i = 1; i < term.rows; i++) { for (let i = 1; i < term.rows; i++) {
assert.deepEqual(term.buffer.lines.get(i), TerminalLine.blankLine(term.cols, DEFAULT_ATTR)); assert.deepEqual(term.buffer.lines.get(i), BufferLine.blankLine(term.cols, DEFAULT_ATTR));
} }
}); });
it('should not break the prompt when cleared twice', () => { it('should not break the prompt when cleared twice', () => {
@@ -172,7 +172,7 @@ describe('term.js addons', () => {
assert.equal(term.buffer.lines.length, term.rows); assert.equal(term.buffer.lines.length, term.rows);
assert.deepEqual(term.buffer.lines.get(0), promptLine); assert.deepEqual(term.buffer.lines.get(0), promptLine);
for (let i = 1; i < term.rows; i++) { for (let i = 1; i < term.rows; i++) {
assert.deepEqual(term.buffer.lines.get(i), TerminalLine.blankLine(term.cols, DEFAULT_ATTR)); assert.deepEqual(term.buffer.lines.get(i), BufferLine.blankLine(term.cols, DEFAULT_ATTR));
} }
}); });
}); });
+4 -4
View File
@@ -52,7 +52,7 @@ import { DomRenderer } from './renderer/dom/DomRenderer';
import { IKeyboardEvent } from './common/Types'; import { IKeyboardEvent } from './common/Types';
import { evaluateKeyboardEvent } from './core/input/Keyboard'; import { evaluateKeyboardEvent } from './core/input/Keyboard';
import { KeyboardResultType, ICharset } from './core/Types'; import { KeyboardResultType, ICharset } from './core/Types';
import { TerminalLine } from './TerminalLine'; import { BufferLine } from './TerminalLine';
// Let it work inside Node.js for automated testing purposes. // Let it work inside Node.js for automated testing purposes.
const document = (typeof window !== 'undefined') ? window.document : null; const document = (typeof window !== 'undefined') ? window.document : null;
@@ -1171,7 +1171,7 @@ export class Terminal extends EventEmitter implements ITerminal, IDisposable, II
* @param isWrapped Whether the new line is wrapped from the previous line. * @param isWrapped Whether the new line is wrapped from the previous line.
*/ */
public scroll(isWrapped?: boolean): void { public scroll(isWrapped?: boolean): void {
const newLine = TerminalLine.blankLine(this.cols, DEFAULT_ATTR, isWrapped); const newLine = BufferLine.blankLine(this.cols, DEFAULT_ATTR, isWrapped);
const topRow = this.buffer.ybase + this.buffer.scrollTop; const topRow = this.buffer.ybase + this.buffer.scrollTop;
const bottomRow = this.buffer.ybase + this.buffer.scrollBottom; const bottomRow = this.buffer.ybase + this.buffer.scrollBottom;
@@ -1753,7 +1753,7 @@ export class Terminal extends EventEmitter implements ITerminal, IDisposable, II
this.buffer.ybase = 0; this.buffer.ybase = 0;
this.buffer.y = 0; this.buffer.y = 0;
for (let i = 1; i < this.rows; i++) { for (let i = 1; i < this.rows; i++) {
this.buffer.lines.push(TerminalLine.blankLine(this.cols, DEFAULT_ATTR)); this.buffer.lines.push(BufferLine.blankLine(this.cols, DEFAULT_ATTR));
} }
this.refresh(0, this.rows - 1); this.refresh(0, this.rows - 1);
this.emit('scroll', this.buffer.ydisp); this.emit('scroll', this.buffer.ydisp);
@@ -1854,7 +1854,7 @@ export class Terminal extends EventEmitter implements ITerminal, IDisposable, II
// blankLine(true) is xterm/linux behavior // blankLine(true) is xterm/linux behavior
const scrollRegionHeight = this.buffer.scrollBottom - this.buffer.scrollTop; const scrollRegionHeight = this.buffer.scrollBottom - this.buffer.scrollTop;
this.buffer.lines.shiftElements(this.buffer.y + this.buffer.ybase, scrollRegionHeight, 1); this.buffer.lines.shiftElements(this.buffer.y + this.buffer.ybase, scrollRegionHeight, 1);
this.buffer.lines.set(this.buffer.y + this.buffer.ybase, TerminalLine.blankLine(this.cols, this.eraseAttr())); this.buffer.lines.set(this.buffer.y + this.buffer.ybase, BufferLine.blankLine(this.cols, this.eraseAttr()));
this.updateRange(this.buffer.scrollTop); this.updateRange(this.buffer.scrollTop);
this.updateRange(this.buffer.scrollBottom); this.updateRange(this.buffer.scrollBottom);
} else { } else {
+21 -14
View File
@@ -3,31 +3,38 @@
* @license MIT * @license MIT
*/ */
import * as chai from 'chai'; import * as chai from 'chai';
import { TerminalLine } from './TerminalLine'; import { BufferLine } from './TerminalLine';
import { CharData } from './Types'; import { CharData, IBufferLine } from './Types';
import { NULL_CELL_CHAR, NULL_CELL_WIDTH, NULL_CELL_CODE, CHAR_DATA_ATTR_INDEX, CHAR_DATA_CHAR_INDEX, CHAR_DATA_WIDTH_INDEX, CHAR_DATA_CODE_INDEX } from './Buffer'; import { NULL_CELL_CHAR, NULL_CELL_WIDTH, NULL_CELL_CODE, CHAR_DATA_ATTR_INDEX, CHAR_DATA_CHAR_INDEX, CHAR_DATA_WIDTH_INDEX, CHAR_DATA_CODE_INDEX } from './Buffer';
describe('TerminalLine', function(): void {
class TestBufferLine extends BufferLine {
public toArray(): CharData[] {
return this._data;
}
}
describe('BufferLine', function(): void {
it('ctor', function(): void { it('ctor', function(): void {
let line = new TerminalLine(); let line: IBufferLine = new TestBufferLine();
chai.expect(line.length).equals(0); chai.expect(line.length).equals(0);
chai.expect(line.pop()).equals(undefined); chai.expect(line.pop()).equals(undefined);
chai.expect(line.isWrapped).equals(false); chai.expect(line.isWrapped).equals(false);
line = new TerminalLine(10); line = new TestBufferLine(10);
chai.expect(line.length).equals(10); chai.expect(line.length).equals(10);
chai.expect(line.pop()).eql(TerminalLine.defaultCell); chai.expect(line.pop()).eql(TestBufferLine.defaultCell);
chai.expect(line.isWrapped).equals(false); chai.expect(line.isWrapped).equals(false);
line = new TerminalLine(10, null, true); line = new TestBufferLine(10, null, true);
chai.expect(line.length).equals(10); chai.expect(line.length).equals(10);
chai.expect(line.pop()).eql(TerminalLine.defaultCell); chai.expect(line.pop()).eql(TestBufferLine.defaultCell);
chai.expect(line.isWrapped).equals(true); chai.expect(line.isWrapped).equals(true);
line = new TerminalLine(10, [123, 'a', 456, 789], true); line = new TestBufferLine(10, [123, 'a', 456, 789], true);
chai.expect(line.length).equals(10); chai.expect(line.length).equals(10);
chai.expect(line.pop()).eql([123, 'a', 456, 789]); chai.expect(line.pop()).eql([123, 'a', 456, 789]);
chai.expect(line.isWrapped).equals(true); chai.expect(line.isWrapped).equals(true);
}); });
it('splice', function(): void { it('splice', function(): void {
const line = new TerminalLine(); const line = new TestBufferLine();
const data: CharData[] = [ const data: CharData[] = [
[1, 'a', 0, 0], [1, 'a', 0, 0],
[2, 'b', 0, 0], [2, 'b', 0, 0],
@@ -41,7 +48,7 @@ describe('TerminalLine', function(): void {
chai.expect(line.toArray()).eql(data); chai.expect(line.toArray()).eql(data);
}); });
it('TerminalLine.blankLine', function(): void { it('TerminalLine.blankLine', function(): void {
const line = TerminalLine.blankLine(5, 123); const line = TestBufferLine.blankLine(5, 123);
chai.expect(line.length).equals(5); chai.expect(line.length).equals(5);
chai.expect(line.isWrapped).equals(false); chai.expect(line.isWrapped).equals(false);
const ch = line.get(0); const ch = line.get(0);
@@ -51,7 +58,7 @@ describe('TerminalLine', function(): void {
chai.expect(ch[CHAR_DATA_CODE_INDEX]).equals(NULL_CELL_CODE); chai.expect(ch[CHAR_DATA_CODE_INDEX]).equals(NULL_CELL_CODE);
}); });
it('insertCells', function(): void { it('insertCells', function(): void {
const line = new TerminalLine(); const line = new TestBufferLine();
const data: CharData[] = [ const data: CharData[] = [
[1, 'a', 0, 0], [1, 'a', 0, 0],
[2, 'b', 0, 0], [2, 'b', 0, 0],
@@ -62,7 +69,7 @@ describe('TerminalLine', function(): void {
chai.expect(line.toArray()).eql([[1, 'a', 0, 0], [4, 'd', 0, 0], [4, 'd', 0, 0]]); chai.expect(line.toArray()).eql([[1, 'a', 0, 0], [4, 'd', 0, 0], [4, 'd', 0, 0]]);
}); });
it('deleteCells', function(): void { it('deleteCells', function(): void {
const line = new TerminalLine(); const line = new TestBufferLine();
const data: CharData[] = [ const data: CharData[] = [
[1, 'a', 0, 0], [1, 'a', 0, 0],
[2, 'b', 0, 0], [2, 'b', 0, 0],
@@ -75,7 +82,7 @@ describe('TerminalLine', function(): void {
chai.expect(line.toArray()).eql([[1, 'a', 0, 0], [4, 'd', 0, 0], [5, 'e', 0, 0], [6, 'f', 0, 0], [6, 'f', 0, 0]]); chai.expect(line.toArray()).eql([[1, 'a', 0, 0], [4, 'd', 0, 0], [5, 'e', 0, 0], [6, 'f', 0, 0], [6, 'f', 0, 0]]);
}); });
it('replaceCells', function(): void { it('replaceCells', function(): void {
const line = new TerminalLine(); const line = new TestBufferLine();
const data: CharData[] = [ const data: CharData[] = [
[1, 'a', 0, 0], [1, 'a', 0, 0],
[2, 'b', 0, 0], [2, 'b', 0, 0],
+6 -17
View File
@@ -2,7 +2,7 @@
* Copyright (c) 2018 The xterm.js authors. All rights reserved. * Copyright (c) 2018 The xterm.js authors. All rights reserved.
* @license MIT * @license MIT
*/ */
import { CharData } from './Types'; import { CharData, IBufferLine } from './Types';
import { NULL_CELL_CODE, NULL_CELL_WIDTH, NULL_CELL_CHAR } from './Buffer'; import { NULL_CELL_CODE, NULL_CELL_WIDTH, NULL_CELL_CHAR } from './Buffer';
/** /**
@@ -20,13 +20,13 @@ import { NULL_CELL_CODE, NULL_CELL_WIDTH, NULL_CELL_CHAR } from './Buffer';
* - remove push/pop/splice * - remove push/pop/splice
* - implement typed array alternative once string is removed from CharData * - implement typed array alternative once string is removed from CharData
*/ */
export class TerminalLine { export class BufferLine implements IBufferLine {
static defaultCell: CharData = [0, NULL_CELL_CHAR, NULL_CELL_WIDTH, NULL_CELL_CODE]; static defaultCell: CharData = [0, NULL_CELL_CHAR, NULL_CELL_WIDTH, NULL_CELL_CODE];
static blankLine(cols: number, attr: number, isWrapped?: boolean): TerminalLine { static blankLine(cols: number, attr: number, isWrapped?: boolean): BufferLine {
const ch: CharData = [attr, NULL_CELL_CHAR, NULL_CELL_WIDTH, NULL_CELL_CODE]; const ch: CharData = [attr, NULL_CELL_CHAR, NULL_CELL_WIDTH, NULL_CELL_CODE];
return new TerminalLine(cols, ch, isWrapped); return new BufferLine(cols, ch, isWrapped);
} }
private _data: CharData[]; protected _data: CharData[];
public isWrapped = false; public isWrapped = false;
public length: number; public length: number;
@@ -35,7 +35,7 @@ export class TerminalLine {
this.length = this._data.length; this.length = this._data.length;
if (cols) { if (cols) {
if (!ch) { if (!ch) {
ch = TerminalLine.defaultCell; ch = BufferLine.defaultCell;
} }
for (let i = 0; i < cols; i++) { for (let i = 0; i < cols; i++) {
this.push(ch); // Note: the ctor ch is not cloned this.push(ch); // Note: the ctor ch is not cloned
@@ -57,7 +57,6 @@ export class TerminalLine {
// to be removed for typed array // to be removed for typed array
public pop(): CharData | undefined { public pop(): CharData | undefined {
// TODO: unref here, change CharData to [typeof Attributes, ...]
const data = this._data.pop(); const data = this._data.pop();
this.length = this._data.length; this.length = this._data.length;
return data; return data;
@@ -67,25 +66,15 @@ export class TerminalLine {
public push(data: CharData): void { public push(data: CharData): void {
this._data.push(data); this._data.push(data);
this.length = this._data.length; this.length = this._data.length;
// TODO: ref here
} }
// to be removed for typed array // to be removed for typed array
public splice(start: number, deleteCount: number, ...items: CharData[]): CharData[] { public splice(start: number, deleteCount: number, ...items: CharData[]): CharData[] {
const removed = this._data.splice(start, deleteCount, ...items); const removed = this._data.splice(start, deleteCount, ...items);
this.length = this._data.length; this.length = this._data.length;
// TODO: ref new, unref old
return removed; return removed;
} }
/** to be called when a line gets removed */
public release(): void {
// TODO: unref here
}
public toArray(): CharData[] {
return this._data;
}
/** insert n cells ch at pos, right cells are lost (stable length) */ /** insert n cells ch at pos, right cells are lost (stable length) */
public insertCells(pos: number, n: number, ch: CharData): void { public insertCells(pos: number, n: number, ch: CharData): void {
while (n--) { while (n--) {
+17 -2
View File
@@ -7,7 +7,6 @@ import { Terminal as PublicTerminal, ITerminalOptions as IPublicTerminalOptions,
import { IColorSet, IRenderer } from './renderer/Types'; import { IColorSet, IRenderer } from './renderer/Types';
import { IMouseZoneManager } from './ui/Types'; import { IMouseZoneManager } from './ui/Types';
import { ICharset } from './core/Types'; import { ICharset } from './core/Types';
import { TerminalLine } from './TerminalLine';
export type CustomKeyEventHandler = (event: KeyboardEvent) => boolean; export type CustomKeyEventHandler = (event: KeyboardEvent) => boolean;
@@ -272,7 +271,7 @@ export interface ITerminalOptions extends IPublicTerminalOptions {
} }
export interface IBuffer { export interface IBuffer {
readonly lines: ICircularList<TerminalLine>; readonly lines: ICircularList<IBufferLine>;
ydisp: number; ydisp: number;
ybase: number; ybase: number;
y: number; y: number;
@@ -511,3 +510,19 @@ export interface IEscapeSequenceParser extends IDisposable {
setErrorHandler(callback: (state: IParsingState) => IParsingState): void; setErrorHandler(callback: (state: IParsingState) => IParsingState): void;
clearErrorHandler(): void; clearErrorHandler(): void;
} }
/**
* Interface for a line in the terminal buffer.
*/
export interface IBufferLine {
length: number;
isWrapped: boolean;
get(index: number): CharData;
set(index: number, value: CharData): void;
pop(): CharData | undefined;
push(data: CharData): void;
splice(start: number, deleteCount: number, ...items: CharData[]): CharData[];
insertCells(pos: number, n: number, ch: CharData): void;
deleteCells(pos: number, n: number, fill: CharData): void;
replaceCells(start: number, end: number, fill: CharData): void;
}
+2 -3
View File
@@ -3,9 +3,8 @@
* @license MIT * @license MIT
*/ */
import { ITerminal, ICircularList } from '../Types'; import { ITerminal, ICircularList, IBufferLine } from '../Types';
import { C0 } from '../common/data/EscapeSequences'; import { C0 } from '../common/data/EscapeSequences';
import { TerminalLine } from '../TerminalLine';
const enum Direction { const enum Direction {
UP = 'A', UP = 'A',
@@ -19,7 +18,7 @@ export class AltClickHandler {
private _startCol: number; private _startCol: number;
private _endRow: number; private _endRow: number;
private _endCol: number; private _endCol: number;
private _lines: ICircularList<TerminalLine>; private _lines: ICircularList<IBufferLine>;
constructor( constructor(
private _mouseEvent: MouseEvent, private _mouseEvent: MouseEvent,
+6 -5
View File
@@ -5,7 +5,8 @@ import { CircularList } from '../common/CircularList';
import { ICharacterJoinerRegistry } from './Types'; import { ICharacterJoinerRegistry } from './Types';
import { CharacterJoinerRegistry } from './CharacterJoinerRegistry'; import { CharacterJoinerRegistry } from './CharacterJoinerRegistry';
import { TerminalLine } from '../TerminalLine'; import { BufferLine } from '../TerminalLine';
import { IBufferLine } from '../Types';
describe('CharacterJoinerRegistry', () => { describe('CharacterJoinerRegistry', () => {
let registry: ICharacterJoinerRegistry; let registry: ICharacterJoinerRegistry;
@@ -14,13 +15,13 @@ describe('CharacterJoinerRegistry', () => {
const terminal = new MockTerminal(); const terminal = new MockTerminal();
terminal.cols = 16; terminal.cols = 16;
terminal.buffer = new MockBuffer(); terminal.buffer = new MockBuffer();
const lines = new CircularList<TerminalLine>(7); const lines = new CircularList<IBufferLine>(7);
lines.set(0, lineData([['a -> b -> c -> d']])); lines.set(0, lineData([['a -> b -> c -> d']]));
lines.set(1, lineData([['a -> b => c -> d']])); lines.set(1, lineData([['a -> b => c -> d']]));
lines.set(2, lineData([['a -> b -', 0xFFFFFFFF], ['> c -> d', 0]])); lines.set(2, lineData([['a -> b -', 0xFFFFFFFF], ['> c -> d', 0]]));
lines.set(3, lineData([['no joined ranges']])); lines.set(3, lineData([['no joined ranges']]));
lines.set(4, new TerminalLine()); lines.set(4, new BufferLine());
lines.set(5, lineData([['a', 0x11111111], [' -> b -> c -> '], ['d', 0x22222222]])); lines.set(5, lineData([['a', 0x11111111], [' -> b -> c -> '], ['d', 0x22222222]]));
const line6 = lineData([['wi']]); const line6 = lineData([['wi']]);
line6.push([0, '¥', 2, '¥'.charCodeAt(0)]); line6.push([0, '¥', 2, '¥'.charCodeAt(0)]);
@@ -262,8 +263,8 @@ describe('CharacterJoinerRegistry', () => {
type IPartialLineData = ([string] | [string, number]); type IPartialLineData = ([string] | [string, number]);
function lineData(data: IPartialLineData[]): TerminalLine { function lineData(data: IPartialLineData[]): IBufferLine {
const tline = new TerminalLine(); const tline = new BufferLine();
for (let i = 0; i < data.length; ++i) { for (let i = 0; i < data.length; ++i) {
const line = data[i][0]; const line = data[i][0];
const attr = <number>(data[i][1] || 0); const attr = <number>(data[i][1] || 0);
+3 -4
View File
@@ -1,7 +1,6 @@
import { CHAR_DATA_ATTR_INDEX, CHAR_DATA_WIDTH_INDEX, CHAR_DATA_CHAR_INDEX } from '../Buffer'; import { CHAR_DATA_ATTR_INDEX, CHAR_DATA_WIDTH_INDEX, CHAR_DATA_CHAR_INDEX } from '../Buffer';
import { ITerminal } from '../Types'; import { ITerminal, IBufferLine } from '../Types';
import { ICharacterJoinerRegistry, ICharacterJoiner } from './Types'; import { ICharacterJoinerRegistry, ICharacterJoiner } from './Types';
import { TerminalLine } from '../TerminalLine';
export class CharacterJoinerRegistry implements ICharacterJoinerRegistry { export class CharacterJoinerRegistry implements ICharacterJoinerRegistry {
@@ -116,7 +115,7 @@ export class CharacterJoinerRegistry implements ICharacterJoinerRegistry {
* @param startIndex Start position of the range to search in the string (inclusive) * @param startIndex Start position of the range to search in the string (inclusive)
* @param endIndex End position of the range to search in the string (exclusive) * @param endIndex End position of the range to search in the string (exclusive)
*/ */
private _getJoinedRanges(line: string, startIndex: number, endIndex: number, lineData: TerminalLine, startCol: number): [number, number][] { private _getJoinedRanges(line: string, startIndex: number, endIndex: number, lineData: IBufferLine, startCol: number): [number, number][] {
const text = line.substring(startIndex, endIndex); const text = line.substring(startIndex, endIndex);
// At this point we already know that there is at least one joiner so // At this point we already know that there is at least one joiner so
// we can just pull its value and assign it directly rather than // we can just pull its value and assign it directly rather than
@@ -141,7 +140,7 @@ export class CharacterJoinerRegistry implements ICharacterJoinerRegistry {
* @param line Cell data for the relevant line in the terminal * @param line Cell data for the relevant line in the terminal
* @param startCol Offset within the line to start from * @param startCol Offset within the line to start from
*/ */
private _stringRangesToCellRanges(ranges: [number, number][], line: TerminalLine, startCol: number): void { private _stringRangesToCellRanges(ranges: [number, number][], line: IBufferLine, startCol: number): void {
let currentRangeIndex = 0; let currentRangeIndex = 0;
let currentRangeStarted = false; let currentRangeStarted = false;
let currentStringIndex = 0; let currentStringIndex = 0;
@@ -8,12 +8,13 @@ import { assert } from 'chai';
import { DomRendererRowFactory } from './DomRendererRowFactory'; import { DomRendererRowFactory } from './DomRendererRowFactory';
import { DEFAULT_ATTR, NULL_CELL_CODE, NULL_CELL_WIDTH, NULL_CELL_CHAR } from '../../Buffer'; import { DEFAULT_ATTR, NULL_CELL_CODE, NULL_CELL_WIDTH, NULL_CELL_CHAR } from '../../Buffer';
import { FLAGS } from '../Types'; import { FLAGS } from '../Types';
import { TerminalLine } from '../../TerminalLine'; import { BufferLine } from '../../TerminalLine';
import { IBufferLine } from '../../Types';
describe('DomRendererRowFactory', () => { describe('DomRendererRowFactory', () => {
let dom: jsdom.JSDOM; let dom: jsdom.JSDOM;
let rowFactory: DomRendererRowFactory; let rowFactory: DomRendererRowFactory;
let lineData: TerminalLine; let lineData: IBufferLine;
beforeEach(() => { beforeEach(() => {
dom = new jsdom.JSDOM(''); dom = new jsdom.JSDOM('');
@@ -146,8 +147,8 @@ describe('DomRendererRowFactory', () => {
return element.innerHTML; return element.innerHTML;
} }
function createEmptyLineData(cols: number): TerminalLine { function createEmptyLineData(cols: number): IBufferLine {
const lineData = new TerminalLine(); const lineData = new BufferLine();
for (let i = 0; i < cols; i++) { for (let i = 0; i < cols; i++) {
lineData.push([DEFAULT_ATTR, NULL_CELL_CHAR, NULL_CELL_WIDTH, NULL_CELL_CODE]); lineData.push([DEFAULT_ATTR, NULL_CELL_CHAR, NULL_CELL_WIDTH, NULL_CELL_CODE]);
} }
+2 -2
View File
@@ -5,7 +5,7 @@
import { CHAR_DATA_CHAR_INDEX, CHAR_DATA_ATTR_INDEX, CHAR_DATA_WIDTH_INDEX } from '../../Buffer'; import { CHAR_DATA_CHAR_INDEX, CHAR_DATA_ATTR_INDEX, CHAR_DATA_WIDTH_INDEX } from '../../Buffer';
import { FLAGS } from '../Types'; import { FLAGS } from '../Types';
import { TerminalLine } from '../../TerminalLine'; import { IBufferLine } from '../../Types';
export const BOLD_CLASS = 'xterm-bold'; export const BOLD_CLASS = 'xterm-bold';
export const ITALIC_CLASS = 'xterm-italic'; export const ITALIC_CLASS = 'xterm-italic';
@@ -17,7 +17,7 @@ export class DomRendererRowFactory {
) { ) {
} }
public createRow(lineData: TerminalLine, isCursorRow: boolean, cursorX: number, cellWidth: number, cols: number): DocumentFragment { public createRow(lineData: IBufferLine, isCursorRow: boolean, cursorX: number, cellWidth: number, cols: number): DocumentFragment {
const fragment = this._document.createDocumentFragment(); const fragment = this._document.createDocumentFragment();
let colCount = 0; let colCount = 0;
+3 -4
View File
@@ -4,11 +4,10 @@
*/ */
import { IColorSet, IRenderer, IRenderDimensions, IColorManager } from '../renderer/Types'; import { IColorSet, IRenderer, IRenderDimensions, IColorManager } from '../renderer/Types';
import { IInputHandlingTerminal, IViewport, ICompositionHelper, ITerminal, IBuffer, IBufferSet, IBrowser, ICharMeasure, ISelectionManager, ITerminalOptions, ICircularList, ILinkifier, IMouseHelper, ILinkMatcherOptions, XtermListener, CharacterJoinerHandler } from '../Types'; import { IInputHandlingTerminal, IViewport, ICompositionHelper, ITerminal, IBuffer, IBufferSet, IBrowser, ICharMeasure, ISelectionManager, ITerminalOptions, ICircularList, ILinkifier, IMouseHelper, ILinkMatcherOptions, XtermListener, CharacterJoinerHandler, IBufferLine } from '../Types';
import { Buffer } from '../Buffer'; import { Buffer } from '../Buffer';
import * as Browser from '../shared/utils/Browser'; import * as Browser from '../shared/utils/Browser';
import { ITheme, IDisposable, IMarker } from 'xterm'; import { ITheme, IDisposable, IMarker } from 'xterm';
import { TerminalLine } from '../TerminalLine';
export class MockTerminal implements ITerminal { export class MockTerminal implements ITerminal {
markers: IMarker[]; markers: IMarker[];
@@ -285,7 +284,7 @@ export class MockInputHandlingTerminal implements IInputHandlingTerminal {
export class MockBuffer implements IBuffer { export class MockBuffer implements IBuffer {
isCursorInViewport: boolean; isCursorInViewport: boolean;
lines: ICircularList<TerminalLine>; lines: ICircularList<IBufferLine>;
ydisp: number; ydisp: number;
ybase: number; ybase: number;
hasScrollback: boolean; hasScrollback: boolean;
@@ -308,7 +307,7 @@ export class MockBuffer implements IBuffer {
prevStop(x?: number): number { prevStop(x?: number): number {
throw new Error('Method not implemented.'); throw new Error('Method not implemented.');
} }
setLines(lines: ICircularList<TerminalLine>): void { setLines(lines: ICircularList<IBufferLine>): void {
this.lines = lines; this.lines = lines;
} }
} }