Working on basic save for custom editors

This commit is contained in:
Matt Bierner
2019-09-13 22:24:35 -07:00
parent 396020da64
commit 4546a07196
5 changed files with 49 additions and 3 deletions

View File

@@ -1051,6 +1051,15 @@ declare module 'vscode' {
export interface WebviewEditor extends WebviewPanel {
state: WebviewEditorState;
/**
* Fired when the webview editor is saved.
*
* Both `Unchanged` and `Dirty` editors can be saved.
*
* Extensions should call `waitUntil` to signal when the save operation complete
*/
readonly onWillSave: Event<{ waitUntil: (thenable: Thenable<boolean>) => void }>;
}
export interface WebviewEditorProvider {

View File

@@ -16,13 +16,13 @@ import { IProductService } from 'vs/platform/product/common/product';
import { ITelemetryService } from 'vs/platform/telemetry/common/telemetry';
import { ExtHostContext, ExtHostWebviewsShape, IExtHostContext, MainContext, MainThreadWebviewsShape, WebviewPanelHandle, WebviewPanelShowOptions, WebviewPanelViewStateData } from 'vs/workbench/api/common/extHost.protocol';
import { editorGroupToViewColumn, EditorViewColumn, viewColumnToEditorGroup } from 'vs/workbench/api/common/shared/editor';
import { CustomFileEditorInput } from 'vs/workbench/contrib/customEditor/browser/customEditorInput';
import { WebviewInput } from 'vs/workbench/contrib/webview/browser/webviewEditorInput';
import { ICreateWebViewShowOptions, IWebviewEditorService, WebviewInputOptions } from 'vs/workbench/contrib/webview/browser/webviewEditorService';
import { IEditorGroupsService } from 'vs/workbench/services/editor/common/editorGroupsService';
import { IEditorService } from 'vs/workbench/services/editor/common/editorService';
import { IExtensionService } from 'vs/workbench/services/extensions/common/extensions';
import { extHostNamedCustomer } from '../common/extHostCustomers';
import { CustomFileEditorInput } from 'vs/workbench/contrib/customEditor/browser/customEditorInput';
/**
* Bi-directional map between webview handles and inputs.
@@ -253,6 +253,12 @@ export class MainThreadWebviews extends Disposable implements MainThreadWebviews
this._webviewEditorInputs.add(handle, webview);
this.hookupWebviewEventDelegate(handle, webview);
if (webview instanceof CustomFileEditorInput) {
webview.onWillSave(e => {
e.waitUntil(this._proxy.$save(handle));
});
}
try {
await this._proxy.$resolveWebviewEditor(
webview.getResource(),

View File

@@ -573,6 +573,7 @@ export interface ExtHostWebviewsShape {
$onDidDisposeWebviewPanel(handle: WebviewPanelHandle): Promise<void>;
$deserializeWebviewPanel(newWebviewHandle: WebviewPanelHandle, viewType: string, title: string, state: any, position: EditorViewColumn, options: modes.IWebviewOptions & modes.IWebviewPanelOptions): Promise<void>;
$resolveWebviewEditor(resource: UriComponents, newWebviewHandle: WebviewPanelHandle, viewType: string, title: string, state: any, position: EditorViewColumn, options: modes.IWebviewOptions & modes.IWebviewPanelOptions): Promise<void>;
$save(handle: WebviewPanelHandle): Promise<boolean>;
}
export interface MainThreadUrlsShape extends IDisposable {

View File

@@ -224,6 +224,18 @@ export class ExtHostWebviewEditor implements vscode.WebviewEditor {
this._proxy.$setState(this._handle, typeConverters.WebviewEditorState.from(newState));
}
private readonly _onWillSave = new Emitter<{ waitUntil: (thenable: Thenable<boolean>) => void }>();
public readonly onWillSave = this._onWillSave.event;
async _save(): Promise<boolean> {
const waitingOn: Thenable<boolean>[] = [];
this._onWillSave.fire({
waitUntil: (thenable: Thenable<boolean>): void => { waitingOn.push(thenable); },
});
const result = await Promise.all(waitingOn);
return result.every(x => x);
}
public postMessage(message: any): Promise<boolean> {
this.assertNotDisposed();
return this._proxy.$postMessage(this._handle, message);
@@ -422,6 +434,13 @@ export class ExtHostWebviews implements ExtHostWebviewsShape {
return Promise.resolve(provider.resolveWebviewEditor(URI.revive(resource), revivedPanel));
}
async $save(handle: WebviewPanelHandle): Promise<boolean> {
const panel = this.getWebviewPanel(handle);
if (panel) {
return panel._save();
}
return false;
}
}
function convertWebviewOptions(

View File

@@ -4,6 +4,7 @@
*--------------------------------------------------------------------------------------------*/
import { memoize } from 'vs/base/common/decorators';
import { Emitter } from 'vs/base/common/event';
import { UnownedDisposable } from 'vs/base/common/lifecycle';
import { basename } from 'vs/base/common/path';
import { URI } from 'vs/base/common/uri';
@@ -115,7 +116,17 @@ export class CustomFileEditorInput extends WebviewInput {
}
public async save(): Promise<boolean> {
// TODO
return true;
if (!this.isDirty) {
return true;
}
const waitingOn: Promise<boolean>[] = [];
this._onWillSave.fire({
waitUntil: (thenable: Promise<boolean>): void => { waitingOn.push(thenable); },
});
const result = await Promise.all(waitingOn);
return result.every(x => x);
}
private readonly _onWillSave = this._register(new Emitter<{ waitUntil: (thenable: Thenable<boolean>) => void }>());
public readonly onWillSave = this._onWillSave.event;
}