UI: Release ace editor resources on destroy. Improve node script test dialog.
This commit is contained in:
parent
05f47f3796
commit
8abe2f19e1
@ -14,7 +14,7 @@
|
||||
/// limitations under the License.
|
||||
///
|
||||
|
||||
import { Component, ElementRef, Inject, OnInit, Renderer2, ViewChild } from '@angular/core';
|
||||
import { Component, ElementRef, Inject, OnDestroy, OnInit, Renderer2, ViewChild } from '@angular/core';
|
||||
import { MAT_DIALOG_DATA, MatDialogRef } from '@angular/material/dialog';
|
||||
import { Store } from '@ngrx/store';
|
||||
import { AppState } from '@core/core.state';
|
||||
@ -33,7 +33,7 @@ export interface AuditLogDetailsDialogData {
|
||||
templateUrl: './audit-log-details-dialog.component.html',
|
||||
styleUrls: ['./audit-log-details-dialog.component.scss']
|
||||
})
|
||||
export class AuditLogDetailsDialogComponent extends DialogComponent<AuditLogDetailsDialogComponent> implements OnInit {
|
||||
export class AuditLogDetailsDialogComponent extends DialogComponent<AuditLogDetailsDialogComponent> implements OnInit, OnDestroy {
|
||||
|
||||
@ViewChild('actionDataEditor', {static: true})
|
||||
actionDataEditorElmRef: ElementRef;
|
||||
@ -45,6 +45,7 @@ export class AuditLogDetailsDialogComponent extends DialogComponent<AuditLogDeta
|
||||
displayFailureDetails: boolean;
|
||||
actionData: string;
|
||||
actionFailureDetails: string;
|
||||
aceEditors: Ace.Editor[] = [];
|
||||
|
||||
constructor(protected store: Store<AppState>,
|
||||
protected router: Router,
|
||||
@ -66,6 +67,11 @@ export class AuditLogDetailsDialogComponent extends DialogComponent<AuditLogDeta
|
||||
}
|
||||
}
|
||||
|
||||
ngOnDestroy(): void {
|
||||
this.aceEditors.forEach(editor => editor.destroy());
|
||||
super.ngOnDestroy();
|
||||
}
|
||||
|
||||
createEditor(editorElementRef: ElementRef, content: string): void {
|
||||
const editorElement = editorElementRef.nativeElement;
|
||||
let editorOptions: Partial<Ace.EditorOptions> = {
|
||||
@ -86,6 +92,7 @@ export class AuditLogDetailsDialogComponent extends DialogComponent<AuditLogDeta
|
||||
getAce().subscribe(
|
||||
(ace) => {
|
||||
const editor = ace.edit(editorElement, editorOptions);
|
||||
this.aceEditors.push(editor);
|
||||
editor.session.setUseWrapMode(false);
|
||||
editor.setValue(content, -1);
|
||||
this.updateEditorSize(editorElement, content, editor);
|
||||
|
||||
@ -14,7 +14,7 @@
|
||||
/// limitations under the License.
|
||||
///
|
||||
|
||||
import { Component, ElementRef, Inject, OnInit, Renderer2, ViewChild } from '@angular/core';
|
||||
import { Component, ElementRef, Inject, OnDestroy, OnInit, Renderer2, ViewChild } from '@angular/core';
|
||||
import { MAT_DIALOG_DATA, MatDialogRef } from '@angular/material/dialog';
|
||||
import { Store } from '@ngrx/store';
|
||||
import { AppState } from '@core/core.state';
|
||||
@ -40,7 +40,7 @@ export interface EventContentDialogData {
|
||||
templateUrl: './event-content-dialog.component.html',
|
||||
styleUrls: ['./event-content-dialog.component.scss']
|
||||
})
|
||||
export class EventContentDialogComponent extends DialogComponent<EventContentDialogData> implements OnInit {
|
||||
export class EventContentDialogComponent extends DialogComponent<EventContentDialogData> implements OnInit, OnDestroy {
|
||||
|
||||
@ViewChild('eventContentEditor', {static: true})
|
||||
eventContentEditorElmRef: ElementRef;
|
||||
@ -48,6 +48,7 @@ export class EventContentDialogComponent extends DialogComponent<EventContentDia
|
||||
content: string;
|
||||
title: string;
|
||||
contentType: ContentType;
|
||||
aceEditor: Ace.Editor;
|
||||
|
||||
constructor(protected store: Store<AppState>,
|
||||
protected router: Router,
|
||||
@ -65,6 +66,13 @@ export class EventContentDialogComponent extends DialogComponent<EventContentDia
|
||||
this.createEditor(this.eventContentEditorElmRef, this.content);
|
||||
}
|
||||
|
||||
ngOnDestroy(): void {
|
||||
if (this.aceEditor) {
|
||||
this.aceEditor.destroy();
|
||||
}
|
||||
super.ngOnDestroy();
|
||||
}
|
||||
|
||||
isJson(str) {
|
||||
try {
|
||||
return isLiteralObject(JSON.parse(str));
|
||||
@ -116,10 +124,10 @@ export class EventContentDialogComponent extends DialogComponent<EventContentDia
|
||||
editorOptions = {...editorOptions, ...advancedOptions};
|
||||
getAce().subscribe(
|
||||
(ace) => {
|
||||
const editor = ace.edit(editorElement, editorOptions);
|
||||
editor.session.setUseWrapMode(false);
|
||||
editor.setValue(processedContent, -1);
|
||||
this.updateEditorSize(editorElement, processedContent, editor);
|
||||
this.aceEditor = ace.edit(editorElement, editorOptions);
|
||||
this.aceEditor.session.setUseWrapMode(false);
|
||||
this.aceEditor.setValue(processedContent, -1);
|
||||
this.updateEditorSize(editorElement, processedContent, this.aceEditor);
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@ -14,7 +14,7 @@
|
||||
/// limitations under the License.
|
||||
///
|
||||
|
||||
import { AfterViewInit, Component, ElementRef, Inject, Renderer2, ViewChild } from '@angular/core';
|
||||
import { AfterViewInit, Component, ElementRef, Inject, OnDestroy, Renderer2, ViewChild } from '@angular/core';
|
||||
import { MAT_DIALOG_DATA, MatDialogRef } from '@angular/material/dialog';
|
||||
import { Store } from '@ngrx/store';
|
||||
import { AppState } from '@core/core.state';
|
||||
@ -54,7 +54,7 @@ export interface ImportDialogCsvData {
|
||||
styleUrls: ['./import-dialog-csv.component.scss']
|
||||
})
|
||||
export class ImportDialogCsvComponent extends DialogComponent<ImportDialogCsvComponent, boolean>
|
||||
implements AfterViewInit {
|
||||
implements AfterViewInit, OnDestroy {
|
||||
|
||||
@ViewChild('importStepper', {static: true}) importStepper: MatVerticalStepper;
|
||||
|
||||
@ -91,6 +91,8 @@ export class ImportDialogCsvComponent extends DialogComponent<ImportDialogCsvCom
|
||||
isImportData = false;
|
||||
statistical: BulkImportResult;
|
||||
|
||||
aceEditor: Ace.Editor;
|
||||
|
||||
private allowAssignColumn: ImportEntityColumnType[];
|
||||
private initEditorComponent = false;
|
||||
private parseData: CsvToJsonResult;
|
||||
@ -131,6 +133,13 @@ export class ImportDialogCsvComponent extends DialogComponent<ImportDialogCsvCom
|
||||
this.allowAssignColumn = columns.map(column => column.value);
|
||||
}
|
||||
|
||||
ngOnDestroy(): void {
|
||||
if (this.aceEditor) {
|
||||
this.aceEditor.destroy();
|
||||
}
|
||||
super.ngOnDestroy();
|
||||
}
|
||||
|
||||
cancel(): void {
|
||||
this.dialogRef.close(false);
|
||||
}
|
||||
@ -271,10 +280,10 @@ export class ImportDialogCsvComponent extends DialogComponent<ImportDialogCsvCom
|
||||
const content = contents.map(error => error.replace('\n', '')).join('\n');
|
||||
getAce().subscribe(
|
||||
(ace) => {
|
||||
const editor = ace.edit(editorElement, editorOptions);
|
||||
editor.session.setUseWrapMode(false);
|
||||
editor.setValue(content, -1);
|
||||
this.updateEditorSize(editorElement, content, editor);
|
||||
this.aceEditor = ace.edit(editorElement, editorOptions);
|
||||
this.aceEditor.session.setUseWrapMode(false);
|
||||
this.aceEditor.setValue(content, -1);
|
||||
this.updateEditorSize(editorElement, content, this.aceEditor);
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@ -93,6 +93,7 @@ export class CustomActionPrettyResourcesTabsComponent extends PageComponent impl
|
||||
}
|
||||
|
||||
ngOnDestroy(): void {
|
||||
this.aceEditors.forEach(editor => editor.destroy());
|
||||
this.aceResize$.disconnect();
|
||||
}
|
||||
|
||||
|
||||
@ -210,6 +210,7 @@ export class WidgetEditorComponent extends PageComponent implements OnInit, OnDe
|
||||
|
||||
ngOnDestroy(): void {
|
||||
this.window.removeEventListener('message', this.onWindowMessageListener);
|
||||
this.aceEditors.forEach(editor => editor.destroy());
|
||||
this.aceResize$.disconnect();
|
||||
this.rxSubscriptions.forEach((subscription) => {
|
||||
subscription.unsubscribe();
|
||||
@ -599,6 +600,7 @@ export class WidgetEditorComponent extends PageComponent implements OnInit, OnDe
|
||||
config.title = this.widget.widgetName;
|
||||
this.widget.defaultConfig = JSON.stringify(config);
|
||||
this.iframe.attr('data-widget', JSON.stringify(this.widget));
|
||||
// @ts-ignore
|
||||
this.iframe[0].contentWindow.location.reload(true);
|
||||
}
|
||||
|
||||
|
||||
@ -145,6 +145,9 @@ export class CssComponent implements OnInit, OnDestroy, ControlValueAccessor, Va
|
||||
if (this.editorResize$) {
|
||||
this.editorResize$.disconnect();
|
||||
}
|
||||
if (this.cssEditor) {
|
||||
this.cssEditor.destroy();
|
||||
}
|
||||
}
|
||||
|
||||
private onAceEditorResize() {
|
||||
|
||||
@ -18,7 +18,7 @@
|
||||
<form class="tb-node-script-test-dialog"
|
||||
[formGroup]="nodeScriptTestFormGroup" (ngSubmit)="save()">
|
||||
<mat-toolbar fxLayout="row" color="primary">
|
||||
<h2>{{ 'rulenode.test-script-function' | translate }}</h2>
|
||||
<h2>{{ 'rulenode.test-script-function' | translate }} ({{ (scriptLang === scriptLanguage.JS ? 'rulenode.script-lang-java-script' : 'rulenode.script-lang-mvel') | translate }})</h2>
|
||||
<span fxFlex></span>
|
||||
<button mat-button mat-icon-button
|
||||
(click)="cancel()"
|
||||
|
||||
@ -98,6 +98,10 @@ export class NodeScriptTestDialogComponent extends DialogComponent<NodeScriptTes
|
||||
|
||||
contentTypes = ContentType;
|
||||
|
||||
scriptLanguage = ScriptLanguage;
|
||||
|
||||
scriptLang = this.data.scriptLang ? this.data.scriptLang : ScriptLanguage.JS;
|
||||
|
||||
constructor(protected store: Store<AppState>,
|
||||
protected router: Router,
|
||||
@Inject(MAT_DIALOG_DATA) public data: NodeScriptTestDialogData,
|
||||
@ -192,8 +196,7 @@ export class NodeScriptTestDialogComponent extends DialogComponent<NodeScriptTes
|
||||
metadata: this.nodeScriptTestFormGroup.get('metadata').value,
|
||||
script: this.nodeScriptTestFormGroup.get('script').value
|
||||
};
|
||||
const scriptLang = this.data.scriptLang ? this.data.scriptLang : ScriptLanguage.JS;
|
||||
return this.ruleChainService.testScript(inputParams, scriptLang).pipe(
|
||||
return this.ruleChainService.testScript(inputParams, this.scriptLang).pipe(
|
||||
mergeMap((result) => {
|
||||
if (result.error) {
|
||||
this.store.dispatch(new ActionNotificationShow(
|
||||
|
||||
@ -147,6 +147,9 @@ export class HtmlComponent implements OnInit, OnDestroy, ControlValueAccessor, V
|
||||
if (this.editorResize$) {
|
||||
this.editorResize$.disconnect();
|
||||
}
|
||||
if (this.htmlEditor) {
|
||||
this.htmlEditor.destroy();
|
||||
}
|
||||
}
|
||||
|
||||
private onAceEditorResize() {
|
||||
|
||||
@ -228,6 +228,9 @@ export class JsFuncComponent implements OnInit, OnDestroy, ControlValueAccessor,
|
||||
if (this.editorResize$) {
|
||||
this.editorResize$.disconnect();
|
||||
}
|
||||
if (this.jsEditor) {
|
||||
this.jsEditor.destroy();
|
||||
}
|
||||
}
|
||||
|
||||
private onAceEditorResize() {
|
||||
|
||||
@ -181,6 +181,9 @@ export class JsonContentComponent implements OnInit, ControlValueAccessor, Valid
|
||||
if (this.editorResize$) {
|
||||
this.editorResize$.disconnect();
|
||||
}
|
||||
if (this.jsonEditor) {
|
||||
this.jsonEditor.destroy();
|
||||
}
|
||||
}
|
||||
|
||||
private onAceEditorResize() {
|
||||
|
||||
@ -147,6 +147,9 @@ export class JsonObjectEditComponent implements OnInit, ControlValueAccessor, Va
|
||||
if (this.editorResize$) {
|
||||
this.editorResize$.disconnect();
|
||||
}
|
||||
if (this.jsonEditor) {
|
||||
this.jsonEditor.destroy();
|
||||
}
|
||||
}
|
||||
|
||||
private onAceEditorResize() {
|
||||
|
||||
@ -14,7 +14,7 @@
|
||||
/// limitations under the License.
|
||||
///
|
||||
|
||||
import { Component, ElementRef, forwardRef, Input, OnInit, Renderer2, ViewChild } from '@angular/core';
|
||||
import { Component, ElementRef, forwardRef, Input, OnDestroy, OnInit, Renderer2, ViewChild } from '@angular/core';
|
||||
import { NG_VALUE_ACCESSOR } from '@angular/forms';
|
||||
import { Ace } from 'ace-builds';
|
||||
import { coerceBooleanProperty } from '@angular/cdk/coercion';
|
||||
@ -36,7 +36,7 @@ import { getAce } from '@shared/models/ace/ace.models';
|
||||
}
|
||||
]
|
||||
})
|
||||
export class JsonObjectViewComponent implements OnInit {
|
||||
export class JsonObjectViewComponent implements OnInit, OnDestroy {
|
||||
|
||||
@ViewChild('jsonViewer', {static: true})
|
||||
jsonViewerElmRef: ElementRef;
|
||||
@ -112,6 +112,12 @@ export class JsonObjectViewComponent implements OnInit {
|
||||
);
|
||||
}
|
||||
|
||||
ngOnDestroy(): void {
|
||||
if (this.jsonViewer) {
|
||||
this.jsonViewer.destroy();
|
||||
}
|
||||
}
|
||||
|
||||
updateEditorSize(editorElement: any, content: string, editor: Ace.Editor) {
|
||||
let newHeight = 200;
|
||||
let newWidth = 600;
|
||||
|
||||
@ -14,7 +14,7 @@
|
||||
/// limitations under the License.
|
||||
///
|
||||
|
||||
import { Component, ElementRef, forwardRef, Input, OnInit, ViewChild } from '@angular/core';
|
||||
import { Component, ElementRef, forwardRef, Input, OnDestroy, OnInit, ViewChild } from '@angular/core';
|
||||
import { ControlValueAccessor, NG_VALUE_ACCESSOR } from '@angular/forms';
|
||||
import { Ace } from 'ace-builds';
|
||||
import { coerceBooleanProperty } from '@angular/cdk/coercion';
|
||||
@ -32,7 +32,7 @@ import { getAce } from '@shared/models/ace/ace.models';
|
||||
}
|
||||
]
|
||||
})
|
||||
export class MarkdownEditorComponent implements OnInit, ControlValueAccessor {
|
||||
export class MarkdownEditorComponent implements OnInit, ControlValueAccessor, OnDestroy {
|
||||
|
||||
@Input() label: string;
|
||||
|
||||
@ -104,6 +104,12 @@ export class MarkdownEditorComponent implements OnInit, ControlValueAccessor {
|
||||
}
|
||||
}
|
||||
|
||||
ngOnDestroy(): void {
|
||||
if (this.markdownEditor) {
|
||||
this.markdownEditor.destroy();
|
||||
}
|
||||
}
|
||||
|
||||
registerOnChange(fn: any): void {
|
||||
this.propagateChange = fn;
|
||||
}
|
||||
|
||||
@ -129,6 +129,9 @@ export class ProtobufContentComponent implements OnInit, ControlValueAccessor, O
|
||||
if (this.editorResize$) {
|
||||
this.editorResize$.disconnect();
|
||||
}
|
||||
if (this.protobufEditor) {
|
||||
this.protobufEditor.destroy();
|
||||
}
|
||||
}
|
||||
|
||||
registerOnChange(fn: any): void {
|
||||
|
||||
@ -2974,6 +2974,8 @@
|
||||
"ui-resources-load-error": "Failed to load configuration ui resources.",
|
||||
"invalid-target-rulechain": "Unable to resolve target rule chain!",
|
||||
"test-script-function": "Test script function",
|
||||
"script-lang-java-script": "Java Script",
|
||||
"script-lang-mvel": "MVEL",
|
||||
"message": "Message",
|
||||
"message-type": "Message type",
|
||||
"select-message-type": "Select message type",
|
||||
|
||||
@ -1465,4 +1465,32 @@ mat-label {
|
||||
pointer-events: none;
|
||||
}
|
||||
}
|
||||
|
||||
.mat-button-toggle-group.tb-button-toggle-group {
|
||||
&.mat-button-toggle-group-appearance-standard {
|
||||
border: none;
|
||||
.mat-button-toggle+.mat-button-toggle {
|
||||
border-left: none;
|
||||
}
|
||||
}
|
||||
.mat-button-toggle {
|
||||
background: rgba(0, 0, 0, 0.06);
|
||||
height: 32px;
|
||||
align-items: center;
|
||||
display: flex;
|
||||
}
|
||||
.mat-button-toggle-checked .mat-button-toggle-button {
|
||||
background-color: #fff;
|
||||
border-radius: 4px;
|
||||
margin-left: 2px;
|
||||
margin-right: 2px;
|
||||
}
|
||||
.mat-button-toggle-appearance-standard .mat-button-toggle-label-content {
|
||||
line-height: 28px;
|
||||
font-size: 14px;
|
||||
}
|
||||
.mat-button-toggle-checked.mat-button-toggle-appearance-standard:not(.mat-button-toggle-disabled):hover .mat-button-toggle-focus-overlay {
|
||||
opacity: .01;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user