@opensumi/ide-ai-native 3.7.1-next-1739252693.0 → 3.7.1-next-1739424847.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/lib/browser/contrib/intelligent-completions/intelligent-completions.contribution.d.ts +1 -0
- package/lib/browser/contrib/intelligent-completions/intelligent-completions.contribution.d.ts.map +1 -1
- package/lib/browser/contrib/intelligent-completions/intelligent-completions.contribution.js +26 -4
- package/lib/browser/contrib/intelligent-completions/intelligent-completions.contribution.js.map +1 -1
- package/lib/browser/contrib/intelligent-completions/intelligent-completions.controller.d.ts +3 -1
- package/lib/browser/contrib/intelligent-completions/intelligent-completions.controller.d.ts.map +1 -1
- package/lib/browser/contrib/intelligent-completions/intelligent-completions.controller.js +9 -1
- package/lib/browser/contrib/intelligent-completions/intelligent-completions.controller.js.map +1 -1
- package/lib/browser/contrib/terminal/component/terminal-command-suggest-controller.js +2 -2
- package/lib/browser/contrib/terminal/component/terminal-command-suggest-controller.js.map +1 -1
- package/lib/browser/layout/ai-layout.d.ts.map +1 -1
- package/lib/browser/layout/ai-layout.js +2 -2
- package/lib/browser/layout/ai-layout.js.map +1 -1
- package/lib/browser/model/enhanceDecorationsCollection.d.ts +14 -10
- package/lib/browser/model/enhanceDecorationsCollection.d.ts.map +1 -1
- package/lib/browser/model/enhanceDecorationsCollection.js +42 -53
- package/lib/browser/model/enhanceDecorationsCollection.js.map +1 -1
- package/lib/browser/widget/inline-chat/inline-chat-editor.controller.d.ts.map +1 -1
- package/lib/browser/widget/inline-chat/inline-chat-editor.controller.js +1 -2
- package/lib/browser/widget/inline-chat/inline-chat-editor.controller.js.map +1 -1
- package/lib/browser/widget/inline-diff/inline-diff-previewer.d.ts +21 -5
- package/lib/browser/widget/inline-diff/inline-diff-previewer.d.ts.map +1 -1
- package/lib/browser/widget/inline-diff/inline-diff-previewer.js +40 -29
- package/lib/browser/widget/inline-diff/inline-diff-previewer.js.map +1 -1
- package/lib/browser/widget/inline-diff/inline-diff.controller.d.ts +8 -12
- package/lib/browser/widget/inline-diff/inline-diff.controller.d.ts.map +1 -1
- package/lib/browser/widget/inline-diff/inline-diff.controller.js +68 -96
- package/lib/browser/widget/inline-diff/inline-diff.controller.js.map +1 -1
- package/lib/browser/widget/inline-input/inline-input.controller.d.ts.map +1 -1
- package/lib/browser/widget/inline-input/inline-input.controller.js +2 -22
- package/lib/browser/widget/inline-input/inline-input.controller.js.map +1 -1
- package/lib/browser/widget/inline-stream-diff/inline-stream-diff.handler.d.ts +8 -19
- package/lib/browser/widget/inline-stream-diff/inline-stream-diff.handler.d.ts.map +1 -1
- package/lib/browser/widget/inline-stream-diff/inline-stream-diff.handler.js +45 -40
- package/lib/browser/widget/inline-stream-diff/inline-stream-diff.handler.js.map +1 -1
- package/lib/browser/widget/inline-stream-diff/live-preview.component.d.ts +17 -4
- package/lib/browser/widget/inline-stream-diff/live-preview.component.d.ts.map +1 -1
- package/lib/browser/widget/inline-stream-diff/live-preview.component.js +37 -5
- package/lib/browser/widget/inline-stream-diff/live-preview.component.js.map +1 -1
- package/lib/browser/widget/inline-stream-diff/live-preview.decoration.d.ts +6 -10
- package/lib/browser/widget/inline-stream-diff/live-preview.decoration.d.ts.map +1 -1
- package/lib/browser/widget/inline-stream-diff/live-preview.decoration.js +31 -76
- package/lib/browser/widget/inline-stream-diff/live-preview.decoration.js.map +1 -1
- package/package.json +21 -21
- package/src/browser/contrib/intelligent-completions/intelligent-completions.contribution.ts +29 -8
- package/src/browser/contrib/intelligent-completions/intelligent-completions.controller.ts +13 -1
- package/src/browser/contrib/terminal/component/terminal-command-suggest-controller.tsx +1 -1
- package/src/browser/layout/ai-layout.tsx +5 -2
- package/src/browser/model/enhanceDecorationsCollection.ts +62 -77
- package/src/browser/widget/inline-chat/inline-chat-editor.controller.ts +1 -2
- package/src/browser/widget/inline-diff/inline-diff-previewer.ts +50 -33
- package/src/browser/widget/inline-diff/inline-diff.controller.ts +90 -114
- package/src/browser/widget/inline-input/inline-input.controller.ts +3 -27
- package/src/browser/widget/inline-stream-diff/inline-stream-diff.handler.tsx +55 -68
- package/src/browser/widget/inline-stream-diff/live-preview.component.tsx +45 -6
- package/src/browser/widget/inline-stream-diff/live-preview.decoration.tsx +38 -111
- package/lib/browser/model/styles.module.less +0 -7
- package/src/browser/model/styles.module.less +0 -7
|
@@ -6,12 +6,18 @@ import {
|
|
|
6
6
|
Emitter,
|
|
7
7
|
Event,
|
|
8
8
|
IDisposable,
|
|
9
|
-
IEventBus,
|
|
10
9
|
ReplyResponse,
|
|
11
10
|
} from '@opensumi/ide-core-common';
|
|
12
|
-
import { EditorGroupCloseEvent } from '@opensumi/ide-editor/lib/browser';
|
|
13
11
|
import * as monaco from '@opensumi/ide-monaco';
|
|
14
12
|
import { ICodeEditor } from '@opensumi/ide-monaco';
|
|
13
|
+
import {
|
|
14
|
+
IObservable,
|
|
15
|
+
ISettableObservable,
|
|
16
|
+
autorun,
|
|
17
|
+
observableFromEvent,
|
|
18
|
+
observableValue,
|
|
19
|
+
transaction,
|
|
20
|
+
} from '@opensumi/ide-monaco/lib/common/observable';
|
|
15
21
|
|
|
16
22
|
import { BaseAIMonacoEditorController } from '../../contrib/base';
|
|
17
23
|
import { EInlineDiffPreviewMode } from '../../preferences/schema';
|
|
@@ -27,6 +33,8 @@ import {
|
|
|
27
33
|
} from './inline-diff-previewer';
|
|
28
34
|
import { InlineDiffWidget } from './inline-diff-widget';
|
|
29
35
|
|
|
36
|
+
type IInlineDiffPreviewer = BaseInlineDiffPreviewer<InlineDiffWidget | InlineStreamDiffHandler>;
|
|
37
|
+
|
|
30
38
|
export class InlineDiffController extends BaseAIMonacoEditorController {
|
|
31
39
|
public static readonly ID = 'editor.contrib.ai.inline.diff';
|
|
32
40
|
|
|
@@ -38,106 +46,68 @@ export class InlineDiffController extends BaseAIMonacoEditorController {
|
|
|
38
46
|
return this.injector.get(PreferenceService);
|
|
39
47
|
}
|
|
40
48
|
|
|
41
|
-
private get eventBus(): IEventBus {
|
|
42
|
-
return this.injector.get(IEventBus);
|
|
43
|
-
}
|
|
44
|
-
|
|
45
49
|
private readonly _onMaxLineCount = new Emitter<number>();
|
|
46
50
|
public readonly onMaxLineCount: Event<number> = this._onMaxLineCount.event;
|
|
47
51
|
|
|
48
|
-
private
|
|
49
|
-
private
|
|
52
|
+
private previewerStore: Map<string, IInlineDiffPreviewer>;
|
|
53
|
+
private currentPreviewer: ISettableObservable<IInlineDiffPreviewer | undefined>;
|
|
54
|
+
private modelChangeObs: IObservable<monaco.editor.ITextModel, unknown>;
|
|
50
55
|
|
|
51
56
|
mount(): IDisposable {
|
|
57
|
+
this.previewerStore = new Map();
|
|
58
|
+
this.currentPreviewer = observableValue(this, undefined);
|
|
59
|
+
this.modelChangeObs = observableFromEvent<monaco.editor.ITextModel>(
|
|
60
|
+
this,
|
|
61
|
+
this.monacoEditor.onDidChangeModel,
|
|
62
|
+
() => this.monacoEditor.getModel()!,
|
|
63
|
+
);
|
|
64
|
+
|
|
52
65
|
this.featureDisposable.addDispose(
|
|
53
|
-
|
|
54
|
-
const
|
|
55
|
-
|
|
66
|
+
autorun((reader) => {
|
|
67
|
+
const model = this.modelChangeObs.read(reader);
|
|
68
|
+
if (!model) {
|
|
69
|
+
return;
|
|
70
|
+
}
|
|
56
71
|
|
|
57
|
-
|
|
58
|
-
|
|
72
|
+
/**
|
|
73
|
+
* 切换到其他 model 且 previewer 未卸载时
|
|
74
|
+
* 保留 previewer 的实例,仅卸载 previewer 的渲染层
|
|
75
|
+
*/
|
|
76
|
+
const id = model.id;
|
|
77
|
+
const previewer = this.currentPreviewer.read(reader);
|
|
78
|
+
if (previewer && previewer.modelId !== id && !previewer.disposed) {
|
|
79
|
+
previewer.hide();
|
|
59
80
|
}
|
|
81
|
+
|
|
82
|
+
const storedPreview = this.previewerStore.get(model.id);
|
|
83
|
+
transaction((tx) => {
|
|
84
|
+
if (storedPreview && storedPreview.modelId === id) {
|
|
85
|
+
this.currentPreviewer.set(storedPreview, tx);
|
|
86
|
+
storedPreview.resume();
|
|
87
|
+
} else {
|
|
88
|
+
this.currentPreviewer.set(undefined, tx);
|
|
89
|
+
}
|
|
90
|
+
});
|
|
60
91
|
}),
|
|
61
92
|
);
|
|
62
93
|
|
|
63
|
-
this.registerInlineDiffFeature(this.monacoEditor);
|
|
64
|
-
|
|
65
94
|
return this.featureDisposable;
|
|
66
95
|
}
|
|
67
96
|
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
return;
|
|
71
|
-
}
|
|
72
|
-
|
|
73
|
-
// 存储的是快照
|
|
74
|
-
const node = this.previewer.createNodeSnapshot();
|
|
75
|
-
if (node) {
|
|
76
|
-
this._previewerNodeStore.set(key, node as InlineStreamDiffHandler);
|
|
77
|
-
}
|
|
97
|
+
getPreviewer(): IInlineDiffPreviewer | undefined {
|
|
98
|
+
return this.currentPreviewer.get();
|
|
78
99
|
}
|
|
79
100
|
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
if (!node) {
|
|
83
|
-
return;
|
|
84
|
-
}
|
|
85
|
-
|
|
86
|
-
if (node.disposed) {
|
|
87
|
-
this.destroyPreviewer(key);
|
|
101
|
+
private renderDiff(previewer: IInlineDiffPreviewer, data: ReplyResponse) {
|
|
102
|
+
if (!previewer) {
|
|
88
103
|
return;
|
|
89
104
|
}
|
|
90
105
|
|
|
91
|
-
|
|
92
|
-
}
|
|
93
|
-
|
|
94
|
-
restoreState(monacoEditor: monaco.ICodeEditor, node: InlineStreamDiffHandler) {
|
|
95
|
-
const uri = monacoEditor.getModel()?.uri;
|
|
96
|
-
|
|
97
|
-
if (uri) {
|
|
98
|
-
this.previewer = this.injector.get(LiveInlineDiffPreviewer, [monacoEditor]);
|
|
99
|
-
this.previewer.attachNode(node);
|
|
100
|
-
this.listenPreviewer(this.previewer);
|
|
101
|
-
|
|
102
|
-
const dispose = this.previewer.onDispose(() => {
|
|
103
|
-
this.destroyPreviewer();
|
|
104
|
-
dispose.dispose();
|
|
105
|
-
});
|
|
106
|
-
}
|
|
107
|
-
}
|
|
108
|
-
|
|
109
|
-
registerInlineDiffFeature(monacoEditor: monaco.ICodeEditor): void {
|
|
110
|
-
const model = monacoEditor.getModel();
|
|
111
|
-
|
|
112
|
-
this.featureDisposable.addDispose(
|
|
113
|
-
monacoEditor.onWillChangeModel((e) => {
|
|
114
|
-
if (!e.oldModelUrl) {
|
|
115
|
-
return;
|
|
116
|
-
}
|
|
117
|
-
|
|
118
|
-
const urlString = e.oldModelUrl.toString();
|
|
119
|
-
this.storeState(urlString);
|
|
120
|
-
|
|
121
|
-
this.destroyPreviewer();
|
|
122
|
-
}),
|
|
123
|
-
);
|
|
124
|
-
|
|
125
|
-
this.featureDisposable.addDispose(
|
|
126
|
-
monacoEditor.onDidChangeModel((e) => {
|
|
127
|
-
if (!e.newModelUrl) {
|
|
128
|
-
return;
|
|
129
|
-
}
|
|
130
|
-
this.tryRestoreState(monacoEditor, e.newModelUrl.toString());
|
|
131
|
-
}),
|
|
132
|
-
);
|
|
106
|
+
previewer.onData(data);
|
|
133
107
|
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
const uriString = model.uri.toString();
|
|
138
|
-
this.destroyPreviewer(uriString);
|
|
139
|
-
}),
|
|
140
|
-
);
|
|
108
|
+
// 仅在当前 model 中进行流式渲染
|
|
109
|
+
if (this.modelChangeObs.get()?.id === previewer.modelId) {
|
|
110
|
+
previewer.render();
|
|
141
111
|
}
|
|
142
112
|
}
|
|
143
113
|
|
|
@@ -154,6 +124,10 @@ export class InlineDiffController extends BaseAIMonacoEditorController {
|
|
|
154
124
|
const disposable = new Disposable();
|
|
155
125
|
|
|
156
126
|
const previewer = this.createDiffPreviewer(monacoEditor, crossSelection, options.previewerOptions);
|
|
127
|
+
transaction((tx) => {
|
|
128
|
+
this.currentPreviewer.set(previewer, tx);
|
|
129
|
+
this.previewerStore.set(previewer.modelId, previewer);
|
|
130
|
+
});
|
|
157
131
|
|
|
158
132
|
const onFinish = () => {
|
|
159
133
|
previewer.layout();
|
|
@@ -168,7 +142,7 @@ export class InlineDiffController extends BaseAIMonacoEditorController {
|
|
|
168
142
|
disposable.addDispose([
|
|
169
143
|
controller.onData((data) => {
|
|
170
144
|
if (ReplyResponse.is(data)) {
|
|
171
|
-
|
|
145
|
+
this.renderDiff(previewer, data);
|
|
172
146
|
}
|
|
173
147
|
}),
|
|
174
148
|
controller.onError((error) => {
|
|
@@ -203,59 +177,61 @@ export class InlineDiffController extends BaseAIMonacoEditorController {
|
|
|
203
177
|
EInlineDiffPreviewMode.inlineLive,
|
|
204
178
|
);
|
|
205
179
|
|
|
206
|
-
|
|
180
|
+
let previewer: IInlineDiffPreviewer;
|
|
207
181
|
|
|
208
182
|
if (inlineDiffMode === EInlineDiffPreviewMode.sideBySide) {
|
|
209
|
-
|
|
183
|
+
previewer = this.injector.get(SideBySideInlineDiffWidget, [monacoEditor]);
|
|
210
184
|
} else {
|
|
211
|
-
|
|
185
|
+
previewer = this.injector.get(LiveInlineDiffPreviewer, [monacoEditor]);
|
|
212
186
|
}
|
|
213
187
|
|
|
214
|
-
|
|
215
|
-
|
|
188
|
+
previewer.create(selection, options);
|
|
189
|
+
previewer.show(selection.startLineNumber - 1, selection.endLineNumber - selection.startLineNumber + 2);
|
|
216
190
|
|
|
217
|
-
|
|
191
|
+
previewer.addDispose(previewer.onLineCount((lineCount) => this._onMaxLineCount.fire(lineCount)));
|
|
218
192
|
|
|
219
|
-
|
|
193
|
+
previewer.addDispose(
|
|
194
|
+
Disposable.create(() => {
|
|
195
|
+
this.previewerStore.delete(previewer.modelId);
|
|
196
|
+
}),
|
|
197
|
+
);
|
|
198
|
+
|
|
199
|
+
return previewer;
|
|
220
200
|
}
|
|
221
201
|
|
|
222
|
-
|
|
202
|
+
handleAction(action: EResultKind): void {
|
|
203
|
+
const previewer = this.getPreviewer();
|
|
223
204
|
if (!previewer) {
|
|
224
205
|
return;
|
|
225
206
|
}
|
|
226
207
|
|
|
227
|
-
previewer.
|
|
228
|
-
}
|
|
229
|
-
|
|
230
|
-
getPreviewer(): BaseInlineDiffPreviewer<InlineDiffWidget | InlineStreamDiffHandler> | undefined {
|
|
231
|
-
return this.previewer;
|
|
232
|
-
}
|
|
233
|
-
|
|
234
|
-
getStoredState(uri: string) {
|
|
235
|
-
return this._previewerNodeStore.get(uri);
|
|
236
|
-
}
|
|
237
|
-
|
|
238
|
-
handleAction(action: EResultKind): void {
|
|
239
|
-
this.previewer?.handleAction(action);
|
|
208
|
+
previewer.handleAction(action);
|
|
240
209
|
}
|
|
241
210
|
|
|
242
211
|
getModifyContent() {
|
|
243
|
-
|
|
244
|
-
|
|
212
|
+
const previewer = this.getPreviewer();
|
|
213
|
+
if (!previewer) {
|
|
214
|
+
return;
|
|
215
|
+
}
|
|
245
216
|
|
|
246
|
-
|
|
247
|
-
return this.previewer?.getOriginValue();
|
|
217
|
+
return previewer.getValue();
|
|
248
218
|
}
|
|
249
219
|
|
|
250
|
-
|
|
251
|
-
this.
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
this._previewerNodeStore.delete(uriString);
|
|
220
|
+
getOriginContent() {
|
|
221
|
+
const previewer = this.getPreviewer();
|
|
222
|
+
if (!previewer) {
|
|
223
|
+
return;
|
|
255
224
|
}
|
|
225
|
+
|
|
226
|
+
return previewer.getOriginValue();
|
|
256
227
|
}
|
|
257
228
|
|
|
258
229
|
revealFirstDiff() {
|
|
259
|
-
this.
|
|
230
|
+
const previewer = this.getPreviewer();
|
|
231
|
+
if (!previewer) {
|
|
232
|
+
return;
|
|
233
|
+
}
|
|
234
|
+
|
|
235
|
+
previewer.revealFirstDiff();
|
|
260
236
|
}
|
|
261
237
|
}
|
|
@@ -18,7 +18,6 @@ import { ICodeEditor } from '@opensumi/ide-monaco';
|
|
|
18
18
|
import {
|
|
19
19
|
IObservable,
|
|
20
20
|
ISettableObservable,
|
|
21
|
-
autorun,
|
|
22
21
|
observableFromEvent,
|
|
23
22
|
observableValue,
|
|
24
23
|
} from '@opensumi/ide-monaco/lib/common/observable';
|
|
@@ -101,7 +100,6 @@ export class InlineInputController extends BaseAIMonacoEditorController {
|
|
|
101
100
|
const currentUri = this.monacoEditor.getModel()?.uri.toString();
|
|
102
101
|
|
|
103
102
|
if (currentUri === resource) {
|
|
104
|
-
this.inlineDiffController.destroyPreviewer(currentUri);
|
|
105
103
|
this.hideInput();
|
|
106
104
|
|
|
107
105
|
const message = localize('aiNative.inline.chat.generating.canceled');
|
|
@@ -138,27 +136,6 @@ export class InlineInputController extends BaseAIMonacoEditorController {
|
|
|
138
136
|
}),
|
|
139
137
|
);
|
|
140
138
|
|
|
141
|
-
this.featureDisposable.addDispose(
|
|
142
|
-
autorun((reader) => {
|
|
143
|
-
const model = this.modelChangeObs.read(reader);
|
|
144
|
-
if (!model) {
|
|
145
|
-
return;
|
|
146
|
-
}
|
|
147
|
-
|
|
148
|
-
const storeData = this.inlineInputWidgetStore.get(model.id);
|
|
149
|
-
if (!storeData) {
|
|
150
|
-
this.hideInput();
|
|
151
|
-
return;
|
|
152
|
-
}
|
|
153
|
-
|
|
154
|
-
if (storeData instanceof InlineInputWidgetStoreInEmptyLine) {
|
|
155
|
-
this.showInputInEmptyLine(storeData.getPosition(), this.monacoEditor, storeData.getValue());
|
|
156
|
-
} else if (storeData instanceof InlineInputWidgetStoreInSelection) {
|
|
157
|
-
this.showInputInSelection(storeData.getSelection(), this.monacoEditor, storeData.getValue());
|
|
158
|
-
}
|
|
159
|
-
}),
|
|
160
|
-
);
|
|
161
|
-
|
|
162
139
|
this.featureDisposable.addDispose(this.inputDisposable);
|
|
163
140
|
|
|
164
141
|
return this.featureDisposable;
|
|
@@ -430,7 +407,6 @@ export class InlineInputController extends BaseAIMonacoEditorController {
|
|
|
430
407
|
inlineInputWidget.show({ selection: decorationSelection });
|
|
431
408
|
|
|
432
409
|
this.aiNativeContextKey.inlineInputWidgetIsVisible.set(true);
|
|
433
|
-
this.inlineDiffController.destroyPreviewer(monacoEditor.getModel()?.uri.toString());
|
|
434
410
|
|
|
435
411
|
this.inputDisposable.addDispose(
|
|
436
412
|
inlineInputWidget.onDispose(() => {
|
|
@@ -517,14 +493,14 @@ export class InlineInputController extends BaseAIMonacoEditorController {
|
|
|
517
493
|
}),
|
|
518
494
|
]);
|
|
519
495
|
|
|
520
|
-
chatResponse.listen();
|
|
521
|
-
|
|
522
496
|
const diffPreviewer = this.inlineDiffController.showPreviewerByStream(monacoEditor, {
|
|
523
497
|
crossSelection: decorationSelection,
|
|
524
498
|
chatResponse,
|
|
525
499
|
});
|
|
526
500
|
|
|
527
|
-
diffPreviewer.
|
|
501
|
+
diffPreviewer.mountWidget(inlineInputWidget);
|
|
502
|
+
|
|
503
|
+
chatResponse.listen();
|
|
528
504
|
}
|
|
529
505
|
} else {
|
|
530
506
|
decorationsCollection.clear();
|
|
@@ -3,6 +3,7 @@ import { Disposable, Emitter, Event, FRAME_THREE, Schemes, Uri, randomString, sl
|
|
|
3
3
|
import { ISingleEditOperation } from '@opensumi/ide-editor';
|
|
4
4
|
import { ICodeEditor, ITextModel, Range, Selection } from '@opensumi/ide-monaco';
|
|
5
5
|
import { StandaloneServices } from '@opensumi/ide-monaco/lib/browser/monaco-api/services';
|
|
6
|
+
import { ISettableObservable, observableValue, transaction } from '@opensumi/ide-monaco/lib/common/observable';
|
|
6
7
|
import { LineRange } from '@opensumi/monaco-editor-core/esm/vs/editor/common/core/lineRange';
|
|
7
8
|
import { linesDiffComputers } from '@opensumi/monaco-editor-core/esm/vs/editor/common/diff/linesDiffComputers';
|
|
8
9
|
import { DetailedLineRangeMapping } from '@opensumi/monaco-editor-core/esm/vs/editor/common/diff/rangeMapping';
|
|
@@ -15,7 +16,7 @@ import { IDiffPreviewerOptions, IInlineDiffPreviewerNode } from '../inline-diff/
|
|
|
15
16
|
|
|
16
17
|
import { InlineStreamDiffComputer } from './inline-stream-diff-computer';
|
|
17
18
|
import { IRemovedWidgetState } from './live-preview.component';
|
|
18
|
-
import {
|
|
19
|
+
import { LivePreviewDiffDecorationModel } from './live-preview.decoration';
|
|
19
20
|
|
|
20
21
|
interface IRangeChangeData {
|
|
21
22
|
removedTextLines: string[];
|
|
@@ -29,7 +30,7 @@ interface IRangeChangeData {
|
|
|
29
30
|
| undefined;
|
|
30
31
|
}
|
|
31
32
|
|
|
32
|
-
interface IComputeDiffData {
|
|
33
|
+
export interface IComputeDiffData {
|
|
33
34
|
newFullRangeTextLines: string[];
|
|
34
35
|
changes: IRangeChangeData[];
|
|
35
36
|
activeLine: number;
|
|
@@ -41,14 +42,6 @@ export enum EComputerMode {
|
|
|
41
42
|
default = 'default',
|
|
42
43
|
}
|
|
43
44
|
|
|
44
|
-
export interface IInlineStreamDiffSnapshotData {
|
|
45
|
-
rawOriginalTextLines: string[];
|
|
46
|
-
rawOriginalTextLinesTokens: LineTokens[];
|
|
47
|
-
undoRedoGroup: UndoRedoGroup;
|
|
48
|
-
decorationSnapshotData: ILivePreviewDiffDecorationSnapshotData;
|
|
49
|
-
previewerOptions: IDiffPreviewerOptions;
|
|
50
|
-
}
|
|
51
|
-
|
|
52
45
|
const inlineStreamDiffComputer = new InlineStreamDiffComputer();
|
|
53
46
|
|
|
54
47
|
@Injectable({ multiple: true })
|
|
@@ -64,18 +57,21 @@ export class InlineStreamDiffHandler extends Disposable implements IInlineDiffPr
|
|
|
64
57
|
private originalModel: ITextModel;
|
|
65
58
|
private virtualModel: ITextModel;
|
|
66
59
|
|
|
67
|
-
// Parts that require snapshots
|
|
68
60
|
private rawOriginalTextLines: string[];
|
|
69
61
|
private rawOriginalTextLinesTokens: LineTokens[] = [];
|
|
70
|
-
private undoRedoGroup: UndoRedoGroup;
|
|
62
|
+
private undoRedoGroup: UndoRedoGroup = new UndoRedoGroup();
|
|
63
|
+
|
|
64
|
+
private readonly diffModel: ISettableObservable<IComputeDiffData | undefined> = observableValue(this, undefined);
|
|
65
|
+
private readonly finallyDiffModel: ISettableObservable<IComputeDiffData | undefined> = observableValue(
|
|
66
|
+
this,
|
|
67
|
+
undefined,
|
|
68
|
+
);
|
|
71
69
|
|
|
72
70
|
public livePreviewDiffDecorationModel: LivePreviewDiffDecorationModel;
|
|
73
71
|
|
|
74
72
|
constructor(private readonly monacoEditor: ICodeEditor) {
|
|
75
73
|
super();
|
|
76
74
|
|
|
77
|
-
this.undoRedoGroup = new UndoRedoGroup();
|
|
78
|
-
|
|
79
75
|
const modelService = StandaloneServices.get(IModelService);
|
|
80
76
|
this.virtualModel = modelService.createModel(
|
|
81
77
|
'',
|
|
@@ -136,44 +132,6 @@ export class InlineStreamDiffHandler extends Disposable implements IInlineDiffPr
|
|
|
136
132
|
this.livePreviewDiffDecorationModel.initialize(zone);
|
|
137
133
|
}
|
|
138
134
|
|
|
139
|
-
private _snapshotStore: IInlineStreamDiffSnapshotData | undefined;
|
|
140
|
-
restoreSnapshot(snapshot: IInlineStreamDiffSnapshotData): void {
|
|
141
|
-
this._snapshotStore = snapshot;
|
|
142
|
-
const {
|
|
143
|
-
rawOriginalTextLines,
|
|
144
|
-
rawOriginalTextLinesTokens,
|
|
145
|
-
undoRedoGroup,
|
|
146
|
-
decorationSnapshotData,
|
|
147
|
-
previewerOptions,
|
|
148
|
-
} = snapshot;
|
|
149
|
-
|
|
150
|
-
this.setPreviewerOptions(previewerOptions);
|
|
151
|
-
|
|
152
|
-
this.rawOriginalTextLines = rawOriginalTextLines;
|
|
153
|
-
this.rawOriginalTextLinesTokens = rawOriginalTextLinesTokens;
|
|
154
|
-
this.undoRedoGroup = undoRedoGroup;
|
|
155
|
-
|
|
156
|
-
this.livePreviewDiffDecorationModel.initialize(decorationSnapshotData.zone);
|
|
157
|
-
}
|
|
158
|
-
|
|
159
|
-
get currentSnapshotStore(): IInlineStreamDiffSnapshotData | undefined {
|
|
160
|
-
return this._snapshotStore;
|
|
161
|
-
}
|
|
162
|
-
|
|
163
|
-
restoreDecorationSnapshot(decorationSnapshotData: ILivePreviewDiffDecorationSnapshotData): void {
|
|
164
|
-
this.livePreviewDiffDecorationModel.restoreSnapshot(decorationSnapshotData);
|
|
165
|
-
}
|
|
166
|
-
|
|
167
|
-
createSnapshot(): IInlineStreamDiffSnapshotData {
|
|
168
|
-
return {
|
|
169
|
-
rawOriginalTextLines: this.rawOriginalTextLines,
|
|
170
|
-
rawOriginalTextLinesTokens: this.rawOriginalTextLinesTokens,
|
|
171
|
-
undoRedoGroup: this.undoRedoGroup,
|
|
172
|
-
decorationSnapshotData: this.livePreviewDiffDecorationModel.createSnapshot(),
|
|
173
|
-
previewerOptions: this.previewerOptions,
|
|
174
|
-
};
|
|
175
|
-
}
|
|
176
|
-
|
|
177
135
|
getVirtualModelValue() {
|
|
178
136
|
return this.virtualModel.getValue();
|
|
179
137
|
}
|
|
@@ -345,7 +303,7 @@ export class InlineStreamDiffHandler extends Disposable implements IInlineDiffPr
|
|
|
345
303
|
});
|
|
346
304
|
}
|
|
347
305
|
|
|
348
|
-
private
|
|
306
|
+
private renderDiffEdits(diffModel: IComputeDiffData): void {
|
|
349
307
|
const { activeLine, newFullRangeTextLines, pendingRange } = diffModel;
|
|
350
308
|
const eol = this.originalModel.getEOL();
|
|
351
309
|
const zone = this.getZone();
|
|
@@ -466,9 +424,8 @@ export class InlineStreamDiffHandler extends Disposable implements IInlineDiffPr
|
|
|
466
424
|
}
|
|
467
425
|
|
|
468
426
|
private currentEditLine = 0;
|
|
469
|
-
private finallyDiffModel: IComputeDiffData | null = null;
|
|
470
427
|
private isEditing = false;
|
|
471
|
-
|
|
428
|
+
public async rateRenderEditController(): Promise<void> {
|
|
472
429
|
if (this.isEditing === false) {
|
|
473
430
|
this.isEditing = true;
|
|
474
431
|
|
|
@@ -480,15 +437,22 @@ export class InlineStreamDiffHandler extends Disposable implements IInlineDiffPr
|
|
|
480
437
|
const virtualTextLines = this.virtualModel.getLinesContent();
|
|
481
438
|
const currentText = virtualTextLines.slice(0, this.currentEditLine);
|
|
482
439
|
const currentDiffModel = this.computeDiff(this.rawOriginalTextLines, currentText);
|
|
483
|
-
|
|
440
|
+
transaction((tx) => {
|
|
441
|
+
this.diffModel.set(currentDiffModel, tx);
|
|
442
|
+
});
|
|
443
|
+
|
|
444
|
+
if (this.originalModel.id === this.monacoEditor.getModel()?.id) {
|
|
445
|
+
this.renderDiffEdits(currentDiffModel);
|
|
446
|
+
}
|
|
484
447
|
|
|
485
448
|
this.currentEditLine += 1;
|
|
486
449
|
|
|
487
450
|
await sleep(FRAME_THREE);
|
|
488
451
|
}
|
|
489
452
|
|
|
490
|
-
|
|
491
|
-
|
|
453
|
+
const finallyDiffModel = this.finallyDiffModel.get();
|
|
454
|
+
if (finallyDiffModel) {
|
|
455
|
+
this.finallyRender(finallyDiffModel);
|
|
492
456
|
}
|
|
493
457
|
|
|
494
458
|
this.isEditing = false;
|
|
@@ -496,27 +460,50 @@ export class InlineStreamDiffHandler extends Disposable implements IInlineDiffPr
|
|
|
496
460
|
}
|
|
497
461
|
|
|
498
462
|
public addLinesToDiff(newText: string, computerMode: EComputerMode = EComputerMode.default): void {
|
|
499
|
-
this.recompute(computerMode, newText);
|
|
500
|
-
|
|
463
|
+
const diffModel = this.recompute(computerMode, newText);
|
|
464
|
+
transaction((tx) => {
|
|
465
|
+
this.diffModel.set(diffModel, tx);
|
|
466
|
+
});
|
|
501
467
|
}
|
|
502
468
|
|
|
503
469
|
public pushRateFinallyDiffStack(diffModel: IComputeDiffData): void {
|
|
504
|
-
|
|
505
|
-
|
|
506
|
-
|
|
507
|
-
|
|
508
|
-
|
|
509
|
-
|
|
470
|
+
transaction((tx) => {
|
|
471
|
+
this.finallyDiffModel.set(diffModel, tx);
|
|
472
|
+
// 可能存在 rate editor controller 处理完之后接口层流式才结束
|
|
473
|
+
if (this.isEditing === false) {
|
|
474
|
+
this.finallyRender(diffModel);
|
|
475
|
+
}
|
|
476
|
+
});
|
|
510
477
|
}
|
|
511
478
|
|
|
512
479
|
public finallyRender(diffModel: IComputeDiffData): void {
|
|
513
|
-
|
|
480
|
+
transaction((tx) => {
|
|
481
|
+
this.diffModel.set(diffModel, tx);
|
|
482
|
+
});
|
|
483
|
+
|
|
484
|
+
if (this.originalModel.id !== this.monacoEditor.getModel()?.id) {
|
|
485
|
+
return;
|
|
486
|
+
}
|
|
487
|
+
|
|
514
488
|
this.renderPartialEditWidgets(diffModel);
|
|
515
|
-
this.
|
|
489
|
+
this.renderDiffEdits(diffModel);
|
|
516
490
|
this.pushStackElement();
|
|
517
491
|
this.monacoEditor.focus();
|
|
518
492
|
}
|
|
519
493
|
|
|
494
|
+
public hide(): void {
|
|
495
|
+
this.livePreviewDiffDecorationModel.hide();
|
|
496
|
+
}
|
|
497
|
+
|
|
498
|
+
public resume(): void {
|
|
499
|
+
const finallyDiffModel = this.finallyDiffModel.get();
|
|
500
|
+
if (!finallyDiffModel) {
|
|
501
|
+
this.rateRenderEditController();
|
|
502
|
+
}
|
|
503
|
+
|
|
504
|
+
this.livePreviewDiffDecorationModel.resume();
|
|
505
|
+
}
|
|
506
|
+
|
|
520
507
|
acceptAll(): void {
|
|
521
508
|
this.livePreviewDiffDecorationModel.acceptUnProcessed();
|
|
522
509
|
this.dispose();
|
|
@@ -21,6 +21,11 @@ import { LineTokens } from '@opensumi/monaco-editor-core/esm/vs/editor/common/to
|
|
|
21
21
|
import { IOptions, ZoneWidget } from '@opensumi/monaco-editor-core/esm/vs/editor/contrib/zoneWidget/browser/zoneWidget';
|
|
22
22
|
import { UndoRedoGroup } from '@opensumi/monaco-editor-core/esm/vs/platform/undoRedo/common/undoRedo';
|
|
23
23
|
|
|
24
|
+
import {
|
|
25
|
+
DeltaDecorations,
|
|
26
|
+
EnhanceDecorationsCollection,
|
|
27
|
+
IDeltaDecorationsOptions,
|
|
28
|
+
} from '../../model/enhanceDecorationsCollection';
|
|
24
29
|
import { renderLines } from '../ghost-text-widget/index';
|
|
25
30
|
|
|
26
31
|
import styles from './inline-stream-diff.module.less';
|
|
@@ -34,7 +39,7 @@ interface IPartialEditWidgetComponent {
|
|
|
34
39
|
discardSequence: string;
|
|
35
40
|
}
|
|
36
41
|
|
|
37
|
-
|
|
42
|
+
type IWidgetStatus = 'accept' | 'discard' | 'pending';
|
|
38
43
|
|
|
39
44
|
export interface IRemovedWidgetState {
|
|
40
45
|
textLines: ITextLinesTokens[];
|
|
@@ -141,7 +146,7 @@ export class AcceptPartialEditWidget extends ReactInlineContentWidget {
|
|
|
141
146
|
private readonly keybindingRegistry: KeybindingRegistry;
|
|
142
147
|
|
|
143
148
|
private _id: string;
|
|
144
|
-
private
|
|
149
|
+
private _addedRangeId: string;
|
|
145
150
|
|
|
146
151
|
private readonly _onAccept = this.registerDispose(new Emitter<void>());
|
|
147
152
|
public readonly onAccept: Event<void> = this._onAccept.event;
|
|
@@ -209,12 +214,12 @@ export class AcceptPartialEditWidget extends ReactInlineContentWidget {
|
|
|
209
214
|
return styles.accept_partial_edit_widget_id;
|
|
210
215
|
}
|
|
211
216
|
|
|
212
|
-
public
|
|
213
|
-
this.
|
|
217
|
+
public recordAddedRangeId(id: string): void {
|
|
218
|
+
this._addedRangeId = id;
|
|
214
219
|
}
|
|
215
220
|
|
|
216
|
-
public
|
|
217
|
-
return this.
|
|
221
|
+
public getAddedRangeId(): string {
|
|
222
|
+
return this._addedRangeId;
|
|
218
223
|
}
|
|
219
224
|
|
|
220
225
|
public resume(): void {
|
|
@@ -314,6 +319,8 @@ export class RemovedZoneWidget extends ZoneWidget {
|
|
|
314
319
|
return this._group;
|
|
315
320
|
}
|
|
316
321
|
|
|
322
|
+
public status: IWidgetStatus = 'pending';
|
|
323
|
+
|
|
317
324
|
constructor(editor: ICodeEditor, public readonly textLines: ITextLinesTokens[], options: IRemovedZoneWidgetOptions) {
|
|
318
325
|
super(editor, options);
|
|
319
326
|
|
|
@@ -362,12 +369,23 @@ export class RemovedZoneWidget extends ZoneWidget {
|
|
|
362
369
|
return this.position || this._recordPosition;
|
|
363
370
|
}
|
|
364
371
|
|
|
372
|
+
accept(): void {
|
|
373
|
+
this.status = 'accept';
|
|
374
|
+
this.hide();
|
|
375
|
+
}
|
|
376
|
+
|
|
377
|
+
discard(): void {
|
|
378
|
+
this.status = 'discard';
|
|
379
|
+
super.hide();
|
|
380
|
+
}
|
|
381
|
+
|
|
365
382
|
hide(): void {
|
|
366
383
|
this._hidden = true;
|
|
367
384
|
super.hide();
|
|
368
385
|
}
|
|
369
386
|
|
|
370
387
|
resume(): void {
|
|
388
|
+
this.status = 'pending';
|
|
371
389
|
const position = this.getLastPosition();
|
|
372
390
|
if (position) {
|
|
373
391
|
this.show(position, this.height);
|
|
@@ -376,6 +394,7 @@ export class RemovedZoneWidget extends ZoneWidget {
|
|
|
376
394
|
|
|
377
395
|
override show(pos: IPosition, heightInLines: number): void {
|
|
378
396
|
this._hidden = false;
|
|
397
|
+
this.status = 'pending';
|
|
379
398
|
super.show(pos, heightInLines);
|
|
380
399
|
}
|
|
381
400
|
|
|
@@ -407,3 +426,23 @@ export class RemovedZoneWidget extends ZoneWidget {
|
|
|
407
426
|
super.dispose();
|
|
408
427
|
}
|
|
409
428
|
}
|
|
429
|
+
|
|
430
|
+
class AddedRangeDeltaDecorations extends DeltaDecorations {
|
|
431
|
+
public status: IWidgetStatus = 'pending';
|
|
432
|
+
|
|
433
|
+
accept(): void {
|
|
434
|
+
this.status = 'accept';
|
|
435
|
+
super.hide();
|
|
436
|
+
}
|
|
437
|
+
|
|
438
|
+
discard(): void {
|
|
439
|
+
this.status = 'discard';
|
|
440
|
+
super.hide();
|
|
441
|
+
}
|
|
442
|
+
}
|
|
443
|
+
|
|
444
|
+
export class AddedRangeDecorationsCollection extends EnhanceDecorationsCollection<AddedRangeDeltaDecorations> {
|
|
445
|
+
protected override createDecorations(metaData: IDeltaDecorationsOptions) {
|
|
446
|
+
return new AddedRangeDeltaDecorations(metaData);
|
|
447
|
+
}
|
|
448
|
+
}
|