diff --git a/apps/red-ui/src/app/modules/shared/components/dictionary-manager/dictionary-manager.component.html b/apps/red-ui/src/app/modules/shared/components/dictionary-manager/dictionary-manager.component.html
index b278a9855..f35b02351 100644
--- a/apps/red-ui/src/app/modules/shared/components/dictionary-manager/dictionary-manager.component.html
+++ b/apps/red-ui/src/app/modules/shared/components/dictionary-manager/dictionary-manager.component.html
@@ -27,8 +27,8 @@
@@ -83,7 +83,6 @@
[diffEditorText]="diffEditorText"
[initialEntries]="initialEntries"
[showDiffEditor]="compare && showDiffEditor"
- (enableSaveButton)="onEnableSaveButton($event)"
>
@@ -97,7 +96,6 @@
(action)="saveDictionary.emit()"
[label]="'dictionary-overview.save-changes' | translate"
[type]="iconButtonTypes.primary"
- [disabled]="!saveButtonEnabled()"
icon="iqser:check"
>
diff --git a/apps/red-ui/src/app/modules/shared/components/dictionary-manager/dictionary-manager.component.ts b/apps/red-ui/src/app/modules/shared/components/dictionary-manager/dictionary-manager.component.ts
index 679c8aa95..7f97a508e 100644
--- a/apps/red-ui/src/app/modules/shared/components/dictionary-manager/dictionary-manager.component.ts
+++ b/apps/red-ui/src/app/modules/shared/components/dictionary-manager/dictionary-manager.component.ts
@@ -1,4 +1,4 @@
-import { ChangeDetectorRef, Component, EventEmitter, Input, OnChanges, Output, signal, SimpleChanges, ViewChild } from '@angular/core';
+import { ChangeDetectorRef, Component, EventEmitter, Input, OnChanges, Output, SimpleChanges, ViewChild } from '@angular/core';
import { Debounce, IconButtonTypes, List, LoadingService } from '@iqser/common-ui';
import { firstValueFrom, Observable, of } from 'rxjs';
import { catchError, map, take, tap } from 'rxjs/operators';
@@ -26,9 +26,6 @@ const HELP_MODE_KEYS = {
styleUrls: ['./dictionary-manager.component.scss'],
})
export class DictionaryManagerComponent implements OnChanges {
- readonly iconButtonTypes = IconButtonTypes;
- readonly saveButtonEnabled = signal(true);
-
@Input() type: DictionaryType = 'dictionary';
@Input() entityType?: string;
@Input() withFloatingActions = true;
@@ -39,6 +36,9 @@ export class DictionaryManagerComponent implements OnChanges {
@Input() isLeavingPage = false;
@Output() readonly saveDictionary = new EventEmitter
();
@ViewChild(EditorComponent) readonly editor: EditorComponent;
+
+ readonly iconButtonTypes = IconButtonTypes;
+
currentMatch = 0;
findMatches: FindMatch[] = [];
diffEditorText = '';
@@ -212,10 +212,6 @@ export class DictionaryManagerComponent implements OnChanges {
}
}
- onEnableSaveButton(value: boolean) {
- this.saveButtonEnabled.set(value);
- }
-
private _applySearchDecorations() {
this._searchDecorations = this.editor.codeEditor?.deltaDecorations(this._searchDecorations, []) || [];
diff --git a/apps/red-ui/src/app/modules/shared/components/editor/editor.component.ts b/apps/red-ui/src/app/modules/shared/components/editor/editor.component.ts
index ad0c13928..b59f54434 100644
--- a/apps/red-ui/src/app/modules/shared/components/editor/editor.component.ts
+++ b/apps/red-ui/src/app/modules/shared/components/editor/editor.component.ts
@@ -1,4 +1,4 @@
-import { Component, EventEmitter, Input, OnChanges, OnInit, Output, SimpleChanges } from '@angular/core';
+import { Component, Input, OnChanges, OnInit, SimpleChanges } from '@angular/core';
import { Debounce, List, LoadingService, OnChange } from '@iqser/common-ui';
import { EditorThemeService } from '@services/editor-theme.service';
import IStandaloneEditorConstructionOptions = monaco.editor.IStandaloneEditorConstructionOptions;
@@ -30,7 +30,6 @@ export class EditorComponent implements OnInit, OnChanges {
@Input() diffEditorText: string;
@Input() @OnChange('revert') initialEntries: List;
@Input() canEdit = false;
- @Output() enableSaveButton = new EventEmitter();
/**
* Used as [modified] input on diff editor
@@ -53,10 +52,18 @@ export class EditorComponent implements OnInit, OnChanges {
return this.currentEntries.toString() !== this.initialEntries.toString();
}
- private get _currentEntriesCount(): number {
+ get #currentEntriesCount(): number {
return this.currentEntries.length;
}
+ @Debounce()
+ codeEditorTextChanged() {
+ const newDecorations = this.#getDecorations();
+ this._decorations = this.codeEditor.deltaDecorations(this._decorations, newDecorations);
+ this.diffValue = this.value;
+ this._loadingService.stop();
+ }
+
ngOnChanges(changes: SimpleChanges) {
if (changes.diffEditorText) {
this._diffEditor?.getOriginalEditor().setValue(this.diffEditorText);
@@ -79,26 +86,17 @@ export class EditorComponent implements OnInit, OnChanges {
onDiffEditorInit(editor: IDiffEditor): void {
this._diffEditor = editor;
this.codeEditor = editor.getModifiedEditor();
- this._addMarginButtons();
- this._diffEditor.getOriginalEditor().onMouseDown(event => this._handleMarginButtonClick(event));
+ this.#addMarginButtons();
+ this._diffEditor.getOriginalEditor().onMouseDown(event => this.#handleMarginButtonClick(event));
this._diffEditor.getModifiedEditor().onDidChangeModelContent(() => {
this.value = this._diffEditor.getModel().modified.getValue();
});
- this._setTheme();
+ this.#setTheme();
}
onCodeEditorInit(editor: ICodeEditor): void {
this.codeEditor = editor;
- this._setTheme();
- }
-
- @Debounce()
- codeEditorTextChanged() {
- const newDecorations = this.currentEntries.filter(entry => this._isNew(entry)).map(entry => this._getDecoration(entry));
- this._decorations = this.codeEditor.deltaDecorations(this._decorations, newDecorations);
- this.diffValue = this.value;
- this._loadingService.stop();
- this.enableSaveButton.emit(true);
+ this.#setTheme();
}
revert() {
@@ -109,28 +107,44 @@ export class EditorComponent implements OnInit, OnChanges {
onPaste() {
this._loadingService.start();
- this.enableSaveButton.emit(false);
}
- private _defineThemes(): void {
+ #getDecorations() {
+ const currentEntries = this.currentEntries;
+ const newDecorations: IModelDeltaDecoration[] = [];
+
+ for (let index = 0; index < currentEntries.length; ++index) {
+ const entry = currentEntries.at(index);
+ if (!this.#isNew(entry)) {
+ continue;
+ }
+
+ const line = index + 1;
+ newDecorations.push(this.#getDecoration(entry, line));
+ }
+
+ return newDecorations;
+ }
+
+ #defineThemes(): void {
for (const theme of this._editorThemeService.themes) {
(window as any).monaco.editor.defineTheme(theme, this._editorThemeService.configurations[theme]);
}
}
- private _setTheme(): void {
- this._defineThemes();
+ #setTheme(): void {
+ this.#defineThemes();
(window as any).monaco.editor.setTheme(this._editorThemeService.getTheme(this.canEdit));
}
- private _handleMarginButtonClick(event: IEditorMouseEvent) {
+ #handleMarginButtonClick(event: IEditorMouseEvent) {
const isMarginButtonClick = event.target.detail.glyphMarginWidth && event.target.detail.glyphMarginWidth !== 0;
if (isMarginButtonClick) {
- this._addContentFromOriginalAtLine(event.target.position.lineNumber);
+ this.#addContentFromOriginalAtLine(event.target.position.lineNumber);
}
}
- private _addContentFromOriginalAtLine(lineNumber: number) {
+ #addContentFromOriginalAtLine(lineNumber: number) {
const lineContent = this._diffEditor.getOriginalEditor().getModel().getLineContent(lineNumber) + '\n';
const lineChanges = this._diffEditor.getLineChanges();
let targetLineNumber = lineNumber;
@@ -141,13 +155,13 @@ export class EditorComponent implements OnInit, OnChanges {
break;
}
}
- const prefix =
- targetLineNumber > this._currentEntriesCount && this.currentEntries[this._currentEntriesCount - 1] !== '' ? '\n' : '';
+ const currentEntriesCount = this.#currentEntriesCount;
+ const prefix = targetLineNumber > currentEntriesCount && this.currentEntries[currentEntriesCount - 1] !== '' ? '\n' : '';
const range = new monaco.Range(targetLineNumber, 1, targetLineNumber, 1);
this._diffEditor.getModifiedEditor().executeEdits(null, [{ range, text: prefix + lineContent, forceMoveMarkers: true }]);
}
- private _addMarginButtons() {
+ #addMarginButtons() {
let glyphDecorations = [];
this._diffEditor.onDidUpdateDiff(() => {
/**
@@ -164,12 +178,11 @@ export class EditorComponent implements OnInit, OnChanges {
});
}
- private _isNew(entry: string): boolean {
+ #isNew(entry: string): boolean {
return this.initialEntries.indexOf(entry) < 0 && entry?.trim().length > 0;
}
- private _getDecoration(entry: string): IModelDeltaDecoration {
- const line = this.currentEntries.indexOf(entry) + 1;
+ #getDecoration(entry: string, line: number): IModelDeltaDecoration {
const cssClass = entry.length < MIN_WORD_LENGTH ? 'too-short-marker' : 'changed-row-marker';
const range = new monaco.Range(line, 1, line, 1);