OSC link progress
This commit is contained in:
@@ -0,0 +1,72 @@
|
||||
/**
|
||||
* Copyright (c) 2022 The xterm.js authors. All rights reserved.
|
||||
* @license MIT
|
||||
*/
|
||||
|
||||
import { ILink, ILinkProvider } from 'browser/Types';
|
||||
import { CellData } from 'common/buffer/CellData';
|
||||
import { IBufferService, IOscLinkService } from 'common/services/Services';
|
||||
|
||||
export class OscLinkProvider implements ILinkProvider {
|
||||
constructor(
|
||||
@IBufferService private readonly _bufferService: IBufferService,
|
||||
@IOscLinkService private readonly _oscLinkService: IOscLinkService
|
||||
) {
|
||||
}
|
||||
|
||||
public provideLinks(y: number, callback: (links: ILink[] | undefined) => void): void {
|
||||
const line = this._bufferService.buffer.lines.get(y - 1);
|
||||
if (!line) {
|
||||
callback(undefined);
|
||||
return;
|
||||
}
|
||||
|
||||
const result: ILink[] = [];
|
||||
const cell = new CellData();
|
||||
const lineLength = line.getTrimmedLength();
|
||||
let currentLinkId = -1;
|
||||
let currentStart = -1;
|
||||
let finishLink = false;
|
||||
for (let x = 0; x < lineLength; x++) {
|
||||
if (!line.hasContent(x)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
line.loadCell(x, cell);
|
||||
if (cell.extended.urlId) {
|
||||
if (currentStart === -1) {
|
||||
currentStart = x;
|
||||
currentLinkId = cell.extended.urlId;
|
||||
continue;
|
||||
} else {
|
||||
finishLink = cell.extended.urlId !== currentLinkId;
|
||||
}
|
||||
} else {
|
||||
if (currentStart !== -1) {
|
||||
finishLink = true;
|
||||
}
|
||||
}
|
||||
|
||||
if (finishLink || (currentStart !== -1 && x === lineLength - 1)) {
|
||||
const text = this._oscLinkService.getLinkData(currentLinkId)?.uri;
|
||||
if (text) {
|
||||
// OSC links always use underline and pointer decorations
|
||||
result.push({
|
||||
text,
|
||||
// These ranges are 1-based
|
||||
range: {
|
||||
start: { x: currentStart + 1, y },
|
||||
end: { x: x + 1, y }
|
||||
},
|
||||
activate(e, text) {
|
||||
console.log('activate!', text);
|
||||
}
|
||||
// TODO: Embedder API to handle hover
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
// TODO: Handle fetching and returning other link ranges to underline other links with the same id
|
||||
callback(result);
|
||||
}
|
||||
}
|
||||
@@ -55,6 +55,7 @@ import { BufferDecorationRenderer } from 'browser/decorations/BufferDecorationRe
|
||||
import { OverviewRulerRenderer } from 'browser/decorations/OverviewRulerRenderer';
|
||||
import { DecorationService } from 'common/services/DecorationService';
|
||||
import { IDecorationService } from 'common/services/Services';
|
||||
import { OscLinkProvider } from 'browser/OscLinkProvider';
|
||||
|
||||
// Let it work inside Node.js for automated testing purposes.
|
||||
const document: Document = (typeof window !== 'undefined') ? window.document : null as any;
|
||||
@@ -163,6 +164,7 @@ export class Terminal extends CoreTerminal implements ITerminal {
|
||||
this._setup();
|
||||
|
||||
this.linkifier2 = this.register(this._instantiationService.createInstance(Linkifier2));
|
||||
this.linkifier2.registerLinkProvider(this._instantiationService.createInstance(OscLinkProvider));
|
||||
this._decorationService = this._instantiationService.createInstance(DecorationService);
|
||||
this._instantiationService.setService(IDecorationService, this._decorationService);
|
||||
|
||||
|
||||
Reference in New Issue
Block a user