mirror of
https://github.com/hexedtech/codemp-vscode.git
synced 2024-11-22 15:34:49 +01:00
feat: leave and detach
This commit is contained in:
parent
509240838b
commit
05a7638761
6 changed files with 72 additions and 16 deletions
11
package.json
11
package.json
|
@ -6,7 +6,7 @@
|
||||||
"homepage": "https://code.mp",
|
"homepage": "https://code.mp",
|
||||||
"repository": "https://github.com/hexedtech/codemp-vscode",
|
"repository": "https://github.com/hexedtech/codemp-vscode",
|
||||||
"publisher": "hexedtech",
|
"publisher": "hexedtech",
|
||||||
"version": "0.1.2",
|
"version": "0.1.3",
|
||||||
"engines": {
|
"engines": {
|
||||||
"vscode": "^1.81.0"
|
"vscode": "^1.81.0"
|
||||||
},
|
},
|
||||||
|
@ -173,7 +173,14 @@
|
||||||
"title": "Jump",
|
"title": "Jump",
|
||||||
"category": "codemp",
|
"category": "codemp",
|
||||||
"icon": "$(debug-console-evaluation-input)"
|
"icon": "$(debug-console-evaluation-input)"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "codemp.forceDesync",
|
||||||
|
"title": "Desync",
|
||||||
|
"category": "codemp"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
],
|
],
|
||||||
"configuration": {
|
"configuration": {
|
||||||
"title": "codemp",
|
"title": "codemp",
|
||||||
|
@ -236,6 +243,6 @@
|
||||||
"typescript": "^5.1.6"
|
"typescript": "^5.1.6"
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"codemp": "^0.7.2"
|
"codemp": "^0.7.3"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -8,10 +8,13 @@ import { LOGGER, provider } from '../extension';
|
||||||
let locks: Map<string, boolean> = new Map();
|
let locks: Map<string, boolean> = new Map();
|
||||||
let autoResync = vscode.workspace.getConfiguration('codemp').get<string>("autoResync");
|
let autoResync = vscode.workspace.getConfiguration('codemp').get<string>("autoResync");
|
||||||
|
|
||||||
export async function apply_changes_to_buffer(path: string, controller: codemp.BufferController | undefined | null, force?: boolean) {
|
export async function apply_changes_to_buffer(path: string, controller: codemp.BufferController, force?: boolean) {
|
||||||
if (workspace === null) throw "can't apply changes while not in a workspace";
|
if (workspace === null) {
|
||||||
if (!controller) controller = workspace.buffer_by_name(path);
|
LOGGER.info(`left workspace, unregistering buffer controller '${path}' callback`);
|
||||||
if (!controller) return;
|
controller.clear_callback();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
let editor = mapping.bufferMapper.visible_by_buffer(path);
|
let editor = mapping.bufferMapper.visible_by_buffer(path);
|
||||||
if (editor === undefined) return;
|
if (editor === undefined) return;
|
||||||
|
|
||||||
|
@ -88,7 +91,6 @@ export async function attach_to_remote_buffer(buffer_name: string, set_content?:
|
||||||
LOGGER.info(`attached to buffer ${buffer_name}`);
|
LOGGER.info(`attached to buffer ${buffer_name}`);
|
||||||
|
|
||||||
let file_uri: vscode.Uri = editor.document.uri;
|
let file_uri: vscode.Uri = editor.document.uri;
|
||||||
mapping.bufferMapper.register(buffer.get_path(), file_uri);
|
|
||||||
let remoteContent = await buffer.content();
|
let remoteContent = await buffer.content();
|
||||||
let localContent = editor.document.getText();
|
let localContent = editor.document.getText();
|
||||||
|
|
||||||
|
@ -110,7 +112,7 @@ export async function attach_to_remote_buffer(buffer_name: string, set_content?:
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
vscode.workspace.onDidChangeTextDocument(async (event: vscode.TextDocumentChangeEvent) => {
|
let disposable = vscode.workspace.onDidChangeTextDocument(async (event: vscode.TextDocumentChangeEvent) => {
|
||||||
if (locks.get(buffer_name)) { return }
|
if (locks.get(buffer_name)) { return }
|
||||||
if (event.document.uri !== file_uri) return; // ?
|
if (event.document.uri !== file_uri) return; // ?
|
||||||
for (let change of event.contentChanges) {
|
for (let change of event.contentChanges) {
|
||||||
|
@ -127,6 +129,8 @@ export async function attach_to_remote_buffer(buffer_name: string, set_content?:
|
||||||
await apply_changes_to_buffer(controller.get_path(), controller)
|
await apply_changes_to_buffer(controller.get_path(), controller)
|
||||||
);
|
);
|
||||||
|
|
||||||
|
mapping.bufferMapper.register(buffer.get_path(), file_uri, disposable);
|
||||||
|
|
||||||
provider.refresh();
|
provider.refresh();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -146,6 +150,26 @@ export async function attach(selected: vscode.TreeItem | undefined) {
|
||||||
await attach_to_remote_buffer(buffer_name);
|
await attach_to_remote_buffer(buffer_name);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export async function detach(selected: vscode.TreeItem | undefined) {
|
||||||
|
if (workspace === null) return vscode.window.showWarningMessage("Not in a workspace");
|
||||||
|
let buffer_name: string | undefined;
|
||||||
|
if (selected !== undefined && selected.label !== undefined) {
|
||||||
|
if (typeof (selected.label) === 'string') {
|
||||||
|
buffer_name = selected.label;
|
||||||
|
} else {
|
||||||
|
buffer_name = selected.label.label; // TODO ughh what is this api?
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
buffer_name = await vscode.window.showInputBox({ prompt: "path of buffer to attach to" });
|
||||||
|
}
|
||||||
|
if (!buffer_name) return;
|
||||||
|
let controller = workspace.buffer_by_name(buffer_name);
|
||||||
|
if (controller) controller.clear_callback();
|
||||||
|
workspace.detach(buffer_name);
|
||||||
|
mapping.bufferMapper.remove(buffer_name);
|
||||||
|
vscode.window.showInformationMessage(`Detached from buffer ${buffer_name}`)
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
export async function share(selected: vscode.TreeItem | undefined) {
|
export async function share(selected: vscode.TreeItem | undefined) {
|
||||||
if (workspace === null) return vscode.window.showWarningMessage("Join a workspace first");
|
if (workspace === null) return vscode.window.showWarningMessage("Join a workspace first");
|
||||||
|
|
|
@ -8,6 +8,7 @@ import { LOGGER, provider } from '../extension';
|
||||||
// TODO this "global state" should probably live elsewher but we need lo update it from these commands
|
// TODO this "global state" should probably live elsewher but we need lo update it from these commands
|
||||||
export let client: codemp.Client | null = null;
|
export let client: codemp.Client | null = null;
|
||||||
export let workspace_list: string[] = [];
|
export let workspace_list: string[] = [];
|
||||||
|
export let cursor_disposable : vscode.Disposable | null;
|
||||||
|
|
||||||
export async function connect() {
|
export async function connect() {
|
||||||
let config = vscode.workspace.getConfiguration('codemp');
|
let config = vscode.workspace.getConfiguration('codemp');
|
||||||
|
@ -61,6 +62,11 @@ export async function join(selected: vscode.TreeItem | undefined) {
|
||||||
controller.callback(async function(controller: codemp.CursorController) {
|
controller.callback(async function(controller: codemp.CursorController) {
|
||||||
while (true) {
|
while (true) {
|
||||||
let event = await controller.try_recv();
|
let event = await controller.try_recv();
|
||||||
|
if (workspace === null) {
|
||||||
|
controller.clear_callback();
|
||||||
|
LOGGER.info("left workspace, stopping cursor controller");
|
||||||
|
return;
|
||||||
|
}
|
||||||
if (event === null) break;
|
if (event === null) break;
|
||||||
if (event.user === undefined) {
|
if (event.user === undefined) {
|
||||||
LOGGER.warn(`Skipping cursor event without user: ${event}`)
|
LOGGER.warn(`Skipping cursor event without user: ${event}`)
|
||||||
|
@ -80,7 +86,7 @@ export async function join(selected: vscode.TreeItem | undefined) {
|
||||||
});
|
});
|
||||||
|
|
||||||
let once = true;
|
let once = true;
|
||||||
vscode.window.onDidChangeTextEditorSelection(async (event: vscode.TextEditorSelectionChangeEvent) => {
|
cursor_disposable = vscode.window.onDidChangeTextEditorSelection(async (event: vscode.TextEditorSelectionChangeEvent) => {
|
||||||
if (event.kind == vscode.TextEditorSelectionChangeKind.Command) return; // TODO commands might move cursor too
|
if (event.kind == vscode.TextEditorSelectionChangeKind.Command) return; // TODO commands might move cursor too
|
||||||
let buf = event.textEditor.document.uri;
|
let buf = event.textEditor.document.uri;
|
||||||
let selection: vscode.Selection = event.selections[0]
|
let selection: vscode.Selection = event.selections[0]
|
||||||
|
@ -138,9 +144,14 @@ export async function join(selected: vscode.TreeItem | undefined) {
|
||||||
provider.refresh();
|
provider.refresh();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export async function leave() {
|
||||||
|
if (!client) throw "can't leave while disconnected";
|
||||||
|
if (!workspace) return vscode.window.showWarningMessage("Not in a workspace");
|
||||||
|
client.leave_workspace(workspace.id());
|
||||||
|
if (cursor_disposable !== null) cursor_disposable.dispose();
|
||||||
|
cursor_disposable = null;
|
||||||
|
setWorkspace(null);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
export async function listWorkspaces() {
|
export async function listWorkspaces() {
|
||||||
|
|
|
@ -8,7 +8,7 @@ import { LOGGER, provider } from '../extension';
|
||||||
export let workspace: codemp.Workspace | null = null;
|
export let workspace: codemp.Workspace | null = null;
|
||||||
|
|
||||||
|
|
||||||
export function setWorkspace(ws: codemp.Workspace) {
|
export function setWorkspace(ws: codemp.Workspace | null) {
|
||||||
workspace = ws;
|
workspace = ws;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -22,8 +22,10 @@ export function activate(context: vscode.ExtensionContext) {
|
||||||
if (workspace === null) return;
|
if (workspace === null) return;
|
||||||
for (let editor of editors) {
|
for (let editor of editors) {
|
||||||
let path = mapping.bufferMapper.by_editor(editor.document.uri);
|
let path = mapping.bufferMapper.by_editor(editor.document.uri);
|
||||||
if (path === undefined) continue;
|
if (!path) continue;
|
||||||
await apply_changes_to_buffer(path, undefined, true);
|
let controller = workspace.buffer_by_name(path);
|
||||||
|
if (!controller) continue;
|
||||||
|
await apply_changes_to_buffer(path, controller, true);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
|
@ -3,11 +3,13 @@ import * as codemp from 'codemp';
|
||||||
|
|
||||||
class BufferMapper {
|
class BufferMapper {
|
||||||
bufferToEditorMapping: Map<string, vscode.Uri> = new Map();
|
bufferToEditorMapping: Map<string, vscode.Uri> = new Map();
|
||||||
|
bufferToDisposableMapping: Map<string, vscode.Disposable> = new Map();
|
||||||
editorToBufferMapping: Map<vscode.Uri, string> = new Map();
|
editorToBufferMapping: Map<vscode.Uri, string> = new Map();
|
||||||
|
|
||||||
public register(buffer: string, uri: vscode.Uri) {
|
public register(buffer: string, uri: vscode.Uri, disposable: vscode.Disposable) {
|
||||||
this.bufferToEditorMapping.set(buffer, uri);
|
this.bufferToEditorMapping.set(buffer, uri);
|
||||||
this.editorToBufferMapping.set(uri, buffer);
|
this.editorToBufferMapping.set(uri, buffer);
|
||||||
|
this.bufferToDisposableMapping.set(buffer, disposable);
|
||||||
}
|
}
|
||||||
|
|
||||||
public uri_by_buffer(name: string): vscode.Uri | undefined {
|
public uri_by_buffer(name: string): vscode.Uri | undefined {
|
||||||
|
@ -24,6 +26,16 @@ class BufferMapper {
|
||||||
return this.editorToBufferMapping.get(name);
|
return this.editorToBufferMapping.get(name);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public remove(name: string) {
|
||||||
|
let uri = this.bufferToEditorMapping.get(name);
|
||||||
|
let disposable = this.bufferToDisposableMapping.get(name);
|
||||||
|
if (disposable) disposable.dispose();
|
||||||
|
if (!uri) return;
|
||||||
|
this.bufferToEditorMapping.delete(name);
|
||||||
|
this.editorToBufferMapping.delete(uri);
|
||||||
|
this.bufferToDisposableMapping.delete(name);
|
||||||
|
}
|
||||||
|
|
||||||
private constructor() { }
|
private constructor() { }
|
||||||
|
|
||||||
public static instance = new BufferMapper();
|
public static instance = new BufferMapper();
|
||||||
|
|
Loading…
Reference in a new issue