Dataset ProfileEditor Validator fixes. More validators added. Table of contents mark invalid entries. Guided tour fix. Fix ng-deep leaks from user listing.
This commit is contained in:
parent
615d30b977
commit
4d6e4fb2cd
|
@ -64,12 +64,31 @@ export class AppComponent implements OnInit, AfterViewInit {
|
|||
ngAfterViewInit(): void {
|
||||
setTimeout(() => {
|
||||
this.sideNavSubscription = this.sidenavService.status().subscribe(isopen=>{
|
||||
const hamburger = document.getElementById('hamburger');
|
||||
if(isopen){
|
||||
//update value of hamburfer
|
||||
document.getElementById('hamburger').classList.add('change');
|
||||
if(!hamburger){//try later
|
||||
setTimeout(() => {
|
||||
const hamburger = document.getElementById('hamburger');
|
||||
if(hamburger){
|
||||
hamburger.classList.add('change');
|
||||
}
|
||||
}, 300);
|
||||
}else{
|
||||
hamburger.classList.add('change');
|
||||
}
|
||||
this.sidenav.open()
|
||||
}else{
|
||||
document.getElementById('hamburger').classList.remove('change');
|
||||
}else{//closed
|
||||
if(!hamburger){//try later
|
||||
setTimeout(() => {
|
||||
const hamburger = document.getElementById('hamburger');
|
||||
if(hamburger){
|
||||
hamburger.classList.remove('change');
|
||||
}
|
||||
}, 300);
|
||||
}else{
|
||||
hamburger.classList.remove('change');
|
||||
}
|
||||
this.sidenav.close();
|
||||
|
||||
}
|
||||
|
|
|
@ -388,7 +388,10 @@ export class GuidedTourComponent implements AfterViewInit, OnDestroy {
|
|||
}
|
||||
|
||||
const scrollAdjustment = this.currentTourStep.scrollAdjustment ? this.currentTourStep.scrollAdjustment : 0;
|
||||
const tourStepHeight = typeof this.tourStep.nativeElement.getBoundingClientRect === 'function' ? this.tourStep.nativeElement.getBoundingClientRect().height : 0;
|
||||
let tourStepHeight = 0;
|
||||
if (this.tourStep != null && this.tourStep.nativeElement != null && typeof this.tourStep.nativeElement.getBoundingClientRect === 'function') {
|
||||
tourStepHeight = this.tourStep.nativeElement.getBoundingClientRect().height;
|
||||
}
|
||||
const elementHeight = this.selectedElementRect.height + scrollAdjustment + tourStepHeight;
|
||||
|
||||
if ((this.windowRef.nativeWindow.innerHeight - this.topOfPageAdjustment) < elementHeight) {
|
||||
|
|
|
@ -67,12 +67,12 @@
|
|||
</div>
|
||||
</div> -->
|
||||
<mat-form-field appearance="none" class="numbering-label" [ngStyle]="calculateLabelWidth(numbering)">
|
||||
<input matInput type="text" [value]="numbering" disabled>
|
||||
<input [ngClass]="{'text-danger':form.get('title').invalid &&form.get('title').touched}" matInput type="text" [value]="numbering" disabled>
|
||||
</mat-form-field>
|
||||
<!-- [appearance]="titleControl.focused? 'legacy':'none'" floatLabel="never" -->
|
||||
<mat-form-field class="col field-title" [appearance]="'none'">
|
||||
<mat-form-field class="col field-title" [appearance]="'none'" floatLabel="never">
|
||||
<input matInput type="text" placeholder="Title" #titleControl="matInput"
|
||||
[formControl]="this.form.get('title')">
|
||||
[formControl]="this.form.get('title')" required>
|
||||
</mat-form-field>
|
||||
</div>
|
||||
</div>
|
||||
|
@ -145,6 +145,7 @@
|
|||
[form]="form.get('fields').get(''+i)" [showOrdinal]="false"
|
||||
[indexPath]="indexPath + 'f' + i" [viewOnly]="viewOnly"
|
||||
[expandView]="hasFocus"
|
||||
[canBeDeleted]="form.get('fields')['controls'].length !=1"
|
||||
(delete)="deleteField(i)">
|
||||
</app-dataset-profile-editor-field-component>
|
||||
</div>
|
||||
|
|
|
@ -32,6 +32,7 @@ import { CurrencyDataEditorModel } from '../../../admin/field-data/currency-data
|
|||
import { ValidationDataEditorModel } from '../../../admin/field-data/validation-data-editor-models';
|
||||
import { DatasetProfileService } from '@app/core/services/dataset-profile/dataset-profile.service';
|
||||
import { OrganizationsDataEditorModel } from '../../../admin/field-data/organizations-data-editor-models';
|
||||
import { EditorCustomValidators } from '../../custom-validators/editor-custom-validators';
|
||||
|
||||
@Component({
|
||||
selector: 'app-dataset-profile-editor-composite-field-component',
|
||||
|
@ -59,6 +60,7 @@ export class DatasetProfileEditorCompositeFieldComponent implements OnInit, OnCh
|
|||
viewStyleEnum = DatasetProfileFieldViewStyle;
|
||||
|
||||
viewTypeEnum = ViewStyleType;
|
||||
private myCustomValidators:EditorCustomValidators = new EditorCustomValidators();
|
||||
|
||||
constructor(
|
||||
private dialog: MatDialog,
|
||||
|
@ -358,15 +360,15 @@ export class DatasetProfileEditorCompositeFieldComponent implements OnInit, OnCh
|
|||
fieldForm.get('viewStyle').get('renderStyle').setValue(DatasetProfileFieldViewStyle.ComboBox)
|
||||
fieldForm.addControl('data', new WordListFieldDataEditorModel().buildForm());
|
||||
|
||||
this.form.get('data').setValidators(this._atLeastOneElementListValidator('options'));
|
||||
this.form.get('data').updateValueAndValidity();
|
||||
fieldForm.get('data').setValidators(this.myCustomValidators.atLeastOneElementListValidator('options'));
|
||||
fieldForm.get('data').updateValueAndValidity();
|
||||
break;
|
||||
case this.viewTypeEnum.Other:
|
||||
fieldForm.get('viewStyle').get('renderStyle').setValue(DatasetProfileFieldViewStyle.ComboBox)
|
||||
fieldForm.addControl('data', new AutoCompleteFieldDataEditorModel().buildForm()); //TODO SEE
|
||||
|
||||
fieldForm.get('data').setValidators(this._atLeastOneElementListValidator('autoCompleteSingleDataList'));
|
||||
|
||||
fieldForm.get('data').setValidators(this.myCustomValidators.atLeastOneElementListValidator('autoCompleteSingleDataList'));
|
||||
fieldForm.get('data').updateValueAndValidity();
|
||||
|
||||
break;
|
||||
case this.viewTypeEnum.InternalDmpEntities:
|
||||
|
@ -380,6 +382,9 @@ export class DatasetProfileEditorCompositeFieldComponent implements OnInit, OnCh
|
|||
case this.viewTypeEnum.RadioBox:
|
||||
fieldForm.get('viewStyle').get('renderStyle').setValue(DatasetProfileFieldViewStyle.RadioBox)
|
||||
fieldForm.addControl('data', new RadioBoxFieldDataEditorModel().buildForm());
|
||||
fieldForm.get('data').setValidators(this.myCustomValidators.atLeastOneElementListValidator('options'));
|
||||
fieldForm.get('data').updateValueAndValidity();
|
||||
|
||||
break;
|
||||
case this.viewTypeEnum.TextArea:
|
||||
fieldForm.get('viewStyle').get('renderStyle').setValue(DatasetProfileFieldViewStyle.TextArea)
|
||||
|
@ -416,7 +421,7 @@ export class DatasetProfileEditorCompositeFieldComponent implements OnInit, OnCh
|
|||
break;
|
||||
case this.viewTypeEnum.Organizations:
|
||||
fieldForm.get('viewStyle').get('renderStyle').setValue(DatasetProfileFieldViewStyle.Organizations)
|
||||
this.form.addControl('data', new OrganizationsDataEditorModel().buildForm());
|
||||
fieldForm.addControl('data', new OrganizationsDataEditorModel().buildForm());
|
||||
// this.form.addControl('data', new OrganizationsDataEditorModel().buildForm())
|
||||
// fieldForm.addControl('data', new DatasetsAutoCompleteFieldDataEditorModel().buildForm()); //TODO
|
||||
break;
|
||||
|
@ -436,7 +441,9 @@ export class DatasetProfileEditorCompositeFieldComponent implements OnInit, OnCh
|
|||
|
||||
(<FormArray>this.form.get('fields')).push(fieldForm);
|
||||
|
||||
// fieldForm.updateValueAndValidity();
|
||||
fieldForm.get('viewStyle').get('renderStyle').updateValueAndValidity();
|
||||
fieldForm.get('data').updateValueAndValidity();
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
@ -488,17 +495,17 @@ export class DatasetProfileEditorCompositeFieldComponent implements OnInit, OnCh
|
|||
// }
|
||||
|
||||
|
||||
private _atLeastOneElementListValidator(arrayToCheck): ValidatorFn{
|
||||
return (control: AbstractControl): ValidationErrors | null=>{
|
||||
// private _atLeastOneElementListValidator(arrayToCheck): ValidatorFn{
|
||||
// return (control: AbstractControl): ValidationErrors | null=>{
|
||||
|
||||
const fa = control.get(arrayToCheck) as FormArray;
|
||||
// const fa = control.get(arrayToCheck) as FormArray;
|
||||
|
||||
if(fa.length === 0){
|
||||
return {emptyArray: true};
|
||||
}
|
||||
return null;
|
||||
}
|
||||
}
|
||||
// if(fa.length === 0){
|
||||
// return {emptyArray: true};
|
||||
// }
|
||||
// return null;
|
||||
// }
|
||||
// }
|
||||
|
||||
|
||||
calculateLabelWidth(numbering: string){
|
||||
|
|
|
@ -12,7 +12,7 @@
|
|||
<li class="list-inline-item" *ngIf="!viewOnly && viewType">
|
||||
<mat-icon style="cursor: pointer;" (click)="addNewRule()" [matTooltip]="'DATASET-PROFILE-EDITOR.ACTIONS.FIELD.ADD-VISIBILITY-RULE' | translate">visibility</mat-icon>
|
||||
</li>
|
||||
<li class="list-inline-item" *ngIf="!viewOnly && viewType">
|
||||
<li class="list-inline-item" *ngIf="!viewOnly && viewType && canBeDeleted">
|
||||
<mat-icon style="cursor: pointer;" (click)="onDelete()" [matTooltip]="'DATASET-PROFILE-EDITOR.ACTIONS.FIELD.DELETE-INPUT' | translate">delete</mat-icon>
|
||||
</li>
|
||||
|
||||
|
|
|
@ -60,7 +60,7 @@ export class DatasetProfileEditorFieldComponent extends BaseComponent implements
|
|||
|
||||
|
||||
@Input() expandView: boolean = true;
|
||||
|
||||
@Input() canBeDeleted:boolean = true;
|
||||
|
||||
@Output() delete = new EventEmitter<void>();
|
||||
|
||||
|
@ -425,7 +425,7 @@ export class DatasetProfileEditorFieldComponent extends BaseComponent implements
|
|||
this.form.get('viewStyle').get('renderStyle').setValue(DatasetProfileFieldViewStyle.ComboBox)
|
||||
this.form.addControl('data', new WordListFieldDataEditorModel().buildForm());
|
||||
|
||||
this.form.get('data').setValidators(this.myCustomValidators._atLeastOneElementListValidator('options'));
|
||||
this.form.get('data').setValidators(this.myCustomValidators.atLeastOneElementListValidator('options'));
|
||||
this.form.get('data').updateValueAndValidity();
|
||||
|
||||
break;
|
||||
|
@ -433,7 +433,7 @@ export class DatasetProfileEditorFieldComponent extends BaseComponent implements
|
|||
this.form.get('viewStyle').get('renderStyle').setValue(DatasetProfileFieldViewStyle.ComboBox)
|
||||
this.form.addControl('data', new AutoCompleteFieldDataEditorModel().buildForm()); //TODO SEE
|
||||
|
||||
this.form.get('data').setValidators(this.myCustomValidators._atLeastOneElementListValidator('autoCompleteSingleDataList'));
|
||||
this.form.get('data').setValidators(this.myCustomValidators.atLeastOneElementListValidator('autoCompleteSingleDataList'));
|
||||
this.form.get('data').updateValueAndValidity();
|
||||
|
||||
|
||||
|
@ -450,7 +450,7 @@ export class DatasetProfileEditorFieldComponent extends BaseComponent implements
|
|||
this.form.get('viewStyle').get('renderStyle').setValue(DatasetProfileFieldViewStyle.RadioBox)
|
||||
this.form.addControl('data', new RadioBoxFieldDataEditorModel().buildForm());
|
||||
|
||||
this.form.get('data').setValidators(this.myCustomValidators._atLeastOneElementListValidator('options'));
|
||||
this.form.get('data').setValidators(this.myCustomValidators.atLeastOneElementListValidator('options'));
|
||||
this.form.get('data').updateValueAndValidity();
|
||||
|
||||
break;
|
||||
|
@ -504,6 +504,10 @@ export class DatasetProfileEditorFieldComponent extends BaseComponent implements
|
|||
this.form.addControl('data', new ValidationDataEditorModel().buildForm());
|
||||
break;
|
||||
}
|
||||
|
||||
this.form.get('data').updateValueAndValidity();
|
||||
this.form.get('viewStyle').get('renderStyle').updateValueAndValidity();
|
||||
this.form.updateValueAndValidity();
|
||||
setTimeout(() => { //TODO
|
||||
this.showPreview = true;
|
||||
});
|
||||
|
|
|
@ -130,6 +130,8 @@ export class DatasetProfileEditorSectionFieldSetComponent extends BaseComponent
|
|||
if(el){
|
||||
el.scrollIntoView({behavior: "smooth"});
|
||||
}
|
||||
}else{//scroll on top
|
||||
window.scrollTo({top:0, behavior:'smooth'});
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -13,7 +13,8 @@
|
|||
<div class="hint col-12">{{'DATASET-PROFILE-EDITOR.STEPS.SECTION-INFO.SECTION-NAME-HINT' | translate}}</div>
|
||||
<mat-form-field class="col-12">
|
||||
<input matInput type="text" placeholder="{{'DATASET-PROFILE-EDITOR.STEPS.FORM.SECTION.FIELDS.TITLE' | translate}}"
|
||||
formControlName="title">
|
||||
formControlName="title" required>
|
||||
<mat-error >{{'GENERAL.VALIDATION.REQUIRED' | translate}}</mat-error>
|
||||
</mat-form-field>
|
||||
<!-- <mat-form-field class="col-md-3">
|
||||
<mat-select placeholder="{{'DATASET-PROFILE-EDITOR.STEPS.FORM.SECTION.FIELDS.PAGE' | translate}}" formControlName="page"
|
||||
|
@ -30,7 +31,8 @@
|
|||
<div class="hint col-12">{{'DATASET-PROFILE-EDITOR.STEPS.SECTION-INFO.SECTION-DESCRIPTION-HINT' | translate}}</div>
|
||||
<mat-form-field class="col-12">
|
||||
<input matInput type="text" placeholder="{{'DATASET-PROFILE-EDITOR.STEPS.FORM.SECTION.FIELDS.DESCRIPTION' | translate}}"
|
||||
formControlName="description">
|
||||
formControlName="description" required>
|
||||
<mat-error >{{'GENERAL.VALIDATION.REQUIRED' | translate}}</mat-error>
|
||||
</mat-form-field>
|
||||
|
||||
|
||||
|
|
|
@ -4,16 +4,64 @@ import { AbstractControl, FormArray, ValidationErrors, ValidatorFn } from "@angu
|
|||
|
||||
export class EditorCustomValidators{
|
||||
|
||||
public _atLeastOneElementListValidator(arrayToCheck): ValidatorFn{
|
||||
public atLeastOneElementListValidator(arrayToCheck): ValidatorFn{
|
||||
return (control: AbstractControl): ValidationErrors | null=>{
|
||||
|
||||
const fa = control.get(arrayToCheck) as FormArray;
|
||||
|
||||
if(fa.length === 0){
|
||||
return {emptyArray: true};
|
||||
return {[EditorCustomValidatorsEnum.emptyArray]: true};
|
||||
}
|
||||
return null;
|
||||
}
|
||||
}
|
||||
public pagesHaveAtLeastOneSection(pagesArrayName:string,sectionsArrayName:string ): ValidatorFn{
|
||||
|
||||
return (control: AbstractControl): ValidationErrors | null=>{
|
||||
|
||||
const pages = control.get(pagesArrayName) as FormArray;
|
||||
const sections = control.get(sectionsArrayName) as FormArray;
|
||||
|
||||
|
||||
const pageIdsArray = pages.controls.map(page=>page.get('id').value);
|
||||
const sectionsPageIds = sections.controls.map(section=> section.get('page').value);
|
||||
|
||||
let invalidMessage = null;
|
||||
|
||||
pageIdsArray.forEach(pageId=>{
|
||||
if(!sectionsPageIds.includes(pageId)){
|
||||
invalidMessage = {[EditorCustomValidatorsEnum.atLeastOneSectionInPage]:true};
|
||||
}
|
||||
})
|
||||
|
||||
return invalidMessage;
|
||||
}
|
||||
}
|
||||
|
||||
public sectionHasAtLeastOneChildOf(fieldsetsArrayName, sectionsArrayName): ValidatorFn{
|
||||
|
||||
return (control: AbstractControl): ValidationErrors | null=>{
|
||||
|
||||
const fieldsets = control.get(fieldsetsArrayName) as FormArray;
|
||||
const sections = control.get(sectionsArrayName) as FormArray;
|
||||
|
||||
|
||||
if((fieldsets && fieldsets.length) || (sections && sections.length)){
|
||||
return null;
|
||||
}
|
||||
|
||||
return {[EditorCustomValidatorsEnum.sectionMustHaveOneChild] : true};
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
export enum EditorCustomValidatorsEnum{
|
||||
sectionMustHaveOneChild = "sectionMustHaveOneChild",
|
||||
atLeastOneSectionInPage = 'atLeastOneSectionInPage',
|
||||
emptyArray="emptyArray"
|
||||
}
|
|
@ -40,7 +40,7 @@
|
|||
<span (click)="stepper.selectedIndex=idx"
|
||||
class="stepper-title-label"
|
||||
[ngClass]="{'stepper-title-label-locked': !isStepUnlocked(idx),'stepper-title-label-completed':idx < stepper.selectedIndex} ">
|
||||
<ng-container *ngIf="isStepCompleted(idx) else numberLabel">
|
||||
<ng-container *ngIf="(step.completed &&(idx!=steps.length-1)) else numberLabel">
|
||||
<mat-icon style="font-size:0.7em; height: 0px;">done</mat-icon>
|
||||
</ng-container>
|
||||
<ng-template #numberLabel>
|
||||
|
@ -119,7 +119,8 @@
|
|||
|
||||
<mat-horizontal-stepper [linear]="true" #stepper class="stepper" (selectionChange)="onMatStepperSelectionChange($event)" style="padding-left: 8px; padding-right: 15px;">
|
||||
|
||||
<mat-step [label]="'DATASET-PROFILE-EDITOR.STEPS.GENERAL-INFO.TITLE' | translate" [stepControl]="basicInfo">
|
||||
<!-- IMPORTANT TO BE !INVALID (WHEN THE TEMPLATE IS FINALIZED THE CONTORLS ARE DISABLED) -->
|
||||
<mat-step [label]="'DATASET-PROFILE-EDITOR.STEPS.GENERAL-INFO.TITLE' | translate" [completed]="(!form.get('label').invalid && !form.get('description').invalid && !form.get('language').invalid)" >
|
||||
<!-- <ng-template matStepLabel>{{'DATASET-PROFILE-EDITOR.STEPS.GENERAL-INFO.TITLE' | translate}}
|
||||
</ng-template> -->
|
||||
<div class="row">
|
||||
|
@ -127,7 +128,7 @@
|
|||
<div class="heading">1.1 {{'DATASET-PROFILE-EDITOR.STEPS.GENERAL-INFO.DATASET-TEMPLATE-NAME'| translate}} *</div>
|
||||
<div class="hint">{{'DATASET-PROFILE-EDITOR.STEPS.GENERAL-INFO.DATASET-TEMPLATE-NAME-HINT'| translate}}</div>
|
||||
<mat-form-field class="full-width basic-info-input">
|
||||
<input matInput formControlName="label"
|
||||
<input matInput [formControl]="form.get('label')"
|
||||
placeholder="{{'DATASET-PROFILE-EDITOR.FIELDS.DATASET-TITLE' | translate}}" required>
|
||||
<mat-error *ngIf="form.get('label').hasError('required')">{{'GENERAL.VALIDATION.REQUIRED' |
|
||||
translate}}
|
||||
|
@ -139,7 +140,7 @@
|
|||
<!-- <div class="hint">{{'DMP-EDITOR.MAIN-INFO.HINT' | translate}}</div> -->
|
||||
<div class="hint">{{'DATASET-PROFILE-EDITOR.STEPS.GENERAL-INFO.DATASET-TEMPLATE-DESCRIPTION-HINT'| translate}}</div>
|
||||
<mat-form-field class="full-width basic-info-input">
|
||||
<textarea matInput formControlName="description" cdkTextareaAutosize cdkAutosizeMinRows="4" cdkAutosizeMaxRows="5"
|
||||
<textarea matInput [formControl]="form.get('description')" cdkTextareaAutosize cdkAutosizeMinRows="4" cdkAutosizeMaxRows="5"
|
||||
placeholder="{{'DATASET-PROFILE-EDITOR.STEPS.GENERAL-INFO.DATASET-TEMPLATE-DESCRIPTION-PLACEHOLDER'| translate}}" required>
|
||||
</textarea>
|
||||
<mat-error *ngIf="form.get('description').hasError('required')">{{'GENERAL.VALIDATION.REQUIRED'
|
||||
|
@ -153,7 +154,7 @@
|
|||
<div class="heading">1.3 {{'DATASET-PROFILE-EDITOR.STEPS.GENERAL-INFO.DATASET-TEMPLATE-LANGUAGE'| translate}} *</div>
|
||||
<mat-form-field class="full-width basic-info-input">
|
||||
<!-- <input matInput formControlName="description" placeholder="{{'DATASET-PROFILE-EDITOR.FIELDS.DATASET-DESCRIPTION' | translate}}" required> -->
|
||||
<mat-select formControlName="language" placeholder="{{'DATASET-PROFILE-EDITOR.STEPS.GENERAL-INFO.DATASET-TEMPLATE-SELECT-LANGUAGE'| translate}}">
|
||||
<mat-select [formControl]="form.get('language')" placeholder="{{'DATASET-PROFILE-EDITOR.STEPS.GENERAL-INFO.DATASET-TEMPLATE-SELECT-LANGUAGE'| translate}}">
|
||||
<mat-option *ngFor="let lang of getLanguageInfos()" [value]="lang.code">
|
||||
{{ lang.name }}
|
||||
</mat-option>
|
||||
|
@ -181,7 +182,7 @@
|
|||
</div>
|
||||
</div>
|
||||
</mat-step> -->
|
||||
<mat-step [label]="'DATASET-PROFILE-EDITOR.STEPS.FORM.TITLE' | translate" [stepControl]="form">
|
||||
<mat-step [label]="'DATASET-PROFILE-EDITOR.STEPS.FORM.TITLE' | translate" [completed]="form.valid">
|
||||
<!-- <ng-template matStepLabel>{{'DATASET-PROFILE-EDITOR.STEPS.FORM.TITLE' | translate}}</ng-template> -->
|
||||
<div class="row">
|
||||
|
||||
|
@ -200,7 +201,8 @@
|
|||
(removeEntry)="onRemoveEntry($event)"
|
||||
[itemSelected]="selectedTocEntry"
|
||||
[viewOnly]="viewOnly"
|
||||
(dataNeedsRefresh)="onDataNeedsRefresh()">
|
||||
(dataNeedsRefresh)="onDataNeedsRefresh()"
|
||||
[colorizeInvalid]="colorizeInvalid">
|
||||
</dataset-profile-table-of-contents>
|
||||
</div>
|
||||
</div>
|
||||
|
@ -224,6 +226,7 @@
|
|||
<div class="hint">{{'DATASET-PROFILE-EDITOR.STEPS.PAGE-INFO.PAGE-NAME-HINT' | translate}}</div>
|
||||
<mat-form-field>
|
||||
<input type="text" matInput formControlName="title">
|
||||
<mat-error >{{'GENERAL.VALIDATION.REQUIRED' | translate}}</mat-error>
|
||||
</mat-form-field>
|
||||
</div>
|
||||
|
||||
|
@ -402,7 +405,7 @@
|
|||
<!-- SAVE BUTTON -->
|
||||
<div class="col-6 d-flex" *ngIf="!viewOnly">
|
||||
<div class="row mt-4">
|
||||
<ng-container *ngIf="false">
|
||||
<ng-container *ngIf="true">
|
||||
<button mat-raised-button class="col-auto mr-2" color="primary" type="button col-auto"
|
||||
(click)='checkFormValidation()'
|
||||
[disabled]="form.valid">{{'DATASET-PROFILE-EDITOR.ACTIONS.VALIDATE' | translate}}</button>
|
||||
|
@ -440,12 +443,20 @@
|
|||
</div>
|
||||
|
||||
</ng-container>
|
||||
<!--
|
||||
<div class="row">
|
||||
|
||||
<!-- <div class="row">
|
||||
<button (click)="printForm()">
|
||||
console form
|
||||
</button>
|
||||
</div> -->
|
||||
<!--
|
||||
<div *ngIf="form">{{form.value | json}}</div>
|
||||
|
||||
<br>
|
||||
<br>
|
||||
<div class="row">
|
||||
{{form.controls?.sections.value |json}}
|
||||
</div> -->
|
||||
|
||||
<!-- {{form.value | json}} -->
|
||||
<!-- <div class="row">
|
||||
|
|
|
@ -41,7 +41,7 @@ import { Rule } from '@app/core/model/dataset-profile-definition/rule';
|
|||
import { DatasetProfileFieldViewStyle } from '@app/core/common/enum/dataset-profile-field-view-style';
|
||||
import { invalid } from '@angular/compiler/src/render3/view/util';
|
||||
import { SideNavService } from '@app/core/services/sidenav/side-nav.sevice';
|
||||
import { EditorCustomValidators } from './custom-validators/editor-custom-validators';
|
||||
import { EditorCustomValidators, EditorCustomValidatorsEnum } from './custom-validators/editor-custom-validators';
|
||||
import { CustomErrorValidator } from '@common/forms/validation/custom-validator';
|
||||
import { STEPPER_ANIMATIONS } from './animations/animations';
|
||||
const skipDisable: any[] = require('../../../../../assets/resources/skipDisable.json');
|
||||
|
@ -72,6 +72,8 @@ export class DatasetProfileEditorComponent extends BaseComponent implements OnIn
|
|||
errorMessages: string[] = [];
|
||||
tocEntryEnumValues = ToCEntryType;
|
||||
|
||||
colorizeInvalid:boolean = false;
|
||||
|
||||
|
||||
customEditorValidators = new EditorCustomValidators();
|
||||
|
||||
|
@ -187,7 +189,7 @@ export class DatasetProfileEditorComponent extends BaseComponent implements OnIn
|
|||
} else {
|
||||
this.dataModel = new DatasetProfileEditorModel();
|
||||
this.form = this.dataModel.buildForm();
|
||||
this.form.setValidators([this.customEditorValidators._atLeastOneElementListValidator('pages'), this.customEditorValidators._atLeastOneElementListValidator('sections')])
|
||||
this.form.setValidators([this.customEditorValidators.atLeastOneElementListValidator('pages'), this.customEditorValidators.pagesHaveAtLeastOneSection('pages', 'sections')])
|
||||
if (this.dataModel.status === DatasetProfileEnum.FINALIZED) {
|
||||
this.form.disable();
|
||||
this.viewOnly = true;
|
||||
|
@ -207,10 +209,11 @@ export class DatasetProfileEditorComponent extends BaseComponent implements OnIn
|
|||
|
||||
prepareForm() {
|
||||
this.visibilityRulesService.buildVisibilityRules([],this.form);
|
||||
this.form.setValidators([this.customEditorValidators._atLeastOneElementListValidator('pages'), this.customEditorValidators._atLeastOneElementListValidator('pages')]);
|
||||
this.form.setValidators([this.customEditorValidators.atLeastOneElementListValidator('pages'),this.customEditorValidators.pagesHaveAtLeastOneSection('pages', 'sections')]);
|
||||
this.form.valueChanges
|
||||
.pipe(takeUntil(this._destroyed))
|
||||
.subscribe(change => {
|
||||
|
||||
// this.datasetProfileService.preview(this.form.value)
|
||||
// .pipe(takeUntil(this._destroyed))
|
||||
// .subscribe(dataset => {
|
||||
|
@ -230,8 +233,6 @@ export class DatasetProfileEditorComponent extends BaseComponent implements OnIn
|
|||
this.selectedTocEntry = tocentries[0];
|
||||
}
|
||||
|
||||
//this.getPreview();
|
||||
|
||||
}
|
||||
|
||||
onIsMultiplicityEnabledChange(isMultiplicityEnabled: boolean) {
|
||||
|
@ -241,11 +242,11 @@ export class DatasetProfileEditorComponent extends BaseComponent implements OnIn
|
|||
}
|
||||
}
|
||||
|
||||
addSection() {
|
||||
const section: SectionEditorModel = new SectionEditorModel();
|
||||
this.dataModel.sections.push(section);
|
||||
(<FormArray>this.form.get('sections')).push(section.buildForm());
|
||||
}
|
||||
// addSection() {
|
||||
// const section: SectionEditorModel = new SectionEditorModel();
|
||||
// this.dataModel.sections.push(section);
|
||||
// (<FormArray>this.form.get('sections')).push(section.buildForm());
|
||||
// }
|
||||
|
||||
addPage() {
|
||||
const page: PageEditorModel = new PageEditorModel(this.dataModel.pages.length);
|
||||
|
@ -376,6 +377,11 @@ export class DatasetProfileEditorComponent extends BaseComponent implements OnIn
|
|||
});
|
||||
}
|
||||
|
||||
updateValidity(){
|
||||
// this.form.updateValueAndValidity();
|
||||
console.log('updagted');
|
||||
}
|
||||
|
||||
getFilenameFromContentDispositionHeader(header: string): string {
|
||||
const regex: RegExp = new RegExp(/filename[^;=\n]*=((['"]).*?\2|[^;\n]*)/g);
|
||||
|
||||
|
@ -399,15 +405,19 @@ export class DatasetProfileEditorComponent extends BaseComponent implements OnIn
|
|||
}
|
||||
|
||||
checkFormValidation() {
|
||||
if (!this.form.valid) {
|
||||
this.nestedIndex = -1;
|
||||
this.form.markAllAsTouched();
|
||||
this.printErrors(this.form);
|
||||
this.showValidationErrorsDialog();
|
||||
this.nestedCount = [];
|
||||
this.nestedIndex = 0;
|
||||
this.errorMessages = [];
|
||||
}
|
||||
this.colorizeInvalid = true;
|
||||
this.printMyErrors(this.form);
|
||||
|
||||
|
||||
// if (!this.form.valid) {
|
||||
// this.nestedIndex = -1;
|
||||
// this.form.markAllAsTouched();
|
||||
// this.printErrors(this.form);
|
||||
// this.showValidationErrorsDialog();
|
||||
// this.nestedCount = [];
|
||||
// this.nestedIndex = 0;
|
||||
// this.errorMessages = [];
|
||||
// }
|
||||
}
|
||||
|
||||
printErrors(rootform: FormGroup) {
|
||||
|
@ -740,7 +750,7 @@ export class DatasetProfileEditorComponent extends BaseComponent implements OnIn
|
|||
// this.dataModel.pages.push(page);
|
||||
|
||||
pagesArray.push(pageForm);
|
||||
|
||||
// this.form.updateValueAndValidity();
|
||||
this.refreshToCEntries();
|
||||
this.selectedTocEntry = this._findTocEntryById(pageForm.get('id').value, this.toCEntries);
|
||||
|
||||
|
@ -757,6 +767,7 @@ export class DatasetProfileEditorComponent extends BaseComponent implements OnIn
|
|||
section.page = parent.id;
|
||||
section.ordinal = sectionsArray.length;
|
||||
sectionsArray.push(section.buildForm());
|
||||
// this.form.updateValueAndValidity();
|
||||
|
||||
} else if( parent.type == ToCEntryType.Section) { //SUBSECTION OF SECTION
|
||||
sectionsArray = parent.form.get('sections') as FormArray;
|
||||
|
@ -774,6 +785,8 @@ export class DatasetProfileEditorComponent extends BaseComponent implements OnIn
|
|||
|
||||
|
||||
const sectionAdded = sectionsArray.at(sectionsArray.length -1) as FormGroup;
|
||||
sectionAdded.setValidators(this.customEditorValidators.sectionHasAtLeastOneChildOf('fieldSets','sections'));
|
||||
sectionAdded.updateValueAndValidity();
|
||||
|
||||
|
||||
this.refreshToCEntries();
|
||||
|
@ -817,7 +830,7 @@ export class DatasetProfileEditorComponent extends BaseComponent implements OnIn
|
|||
break;
|
||||
}
|
||||
|
||||
// this.refreshToCEntries();
|
||||
this.form.updateValueAndValidity();
|
||||
}
|
||||
|
||||
|
||||
|
@ -912,27 +925,29 @@ export class DatasetProfileEditorComponent extends BaseComponent implements OnIn
|
|||
pages.removeAt(pageIndex);
|
||||
//clean up sections of removed page
|
||||
|
||||
const sections = (this.form.get('sections') as FormArray).controls;
|
||||
const sections = (this.form.get('sections') as FormArray);
|
||||
|
||||
const updatedSections = new FormArray([]);
|
||||
const sectionsIndexToBeRemoved = [];
|
||||
|
||||
for (let i = 0; i < sections.length; i++) {
|
||||
let section = sections[i];
|
||||
|
||||
if (section.get('page').value != tce.id) {
|
||||
updatedSections.push(section);
|
||||
sections.controls.forEach((section,idx)=>{
|
||||
if(section.get('page').value === tce.id){
|
||||
sectionsIndexToBeRemoved.push(idx);
|
||||
}
|
||||
}
|
||||
//replace sections value
|
||||
this.form.controls.sections = updatedSections;
|
||||
});
|
||||
|
||||
//update page orders
|
||||
if(sectionsIndexToBeRemoved.length){
|
||||
sectionsIndexToBeRemoved.reverse().forEach(index=>{
|
||||
sections.removeAt(index);
|
||||
});
|
||||
}
|
||||
|
||||
//update page ordinals
|
||||
for(let i=0; i<pages.length; i++){
|
||||
pages.at(i).get('ordinal').patchValue(i);
|
||||
}
|
||||
|
||||
//update validity
|
||||
this.form.controls.sections.updateValueAndValidity();
|
||||
// this.form.controls.sections.updateValueAndValidity();
|
||||
}
|
||||
break;
|
||||
|
||||
|
@ -1028,6 +1043,7 @@ export class DatasetProfileEditorComponent extends BaseComponent implements OnIn
|
|||
//in case selectedtocentrhy is child of the removed element
|
||||
|
||||
this.refreshToCEntries();
|
||||
this.form.updateValueAndValidity();
|
||||
|
||||
}
|
||||
|
||||
|
@ -1339,22 +1355,22 @@ export class DatasetProfileEditorComponent extends BaseComponent implements OnIn
|
|||
|
||||
|
||||
|
||||
get basicInfo(){
|
||||
// get basicInfo(){
|
||||
|
||||
const label = this.form.get('label');
|
||||
const description = this.form.get('description');
|
||||
const language = this.form.get('language');
|
||||
// const label = this.form.get('label');
|
||||
// const description = this.form.get('description');
|
||||
// const language = this.form.get('language');
|
||||
|
||||
|
||||
|
||||
const fg = new FormGroup({
|
||||
label: label,
|
||||
description: description,
|
||||
language: language
|
||||
})
|
||||
// const fg = new FormGroup({
|
||||
// label: label,
|
||||
// description: description,
|
||||
// language: language
|
||||
// })
|
||||
|
||||
return fg;
|
||||
}
|
||||
// return fg;
|
||||
// }
|
||||
|
||||
|
||||
|
||||
|
@ -1421,14 +1437,12 @@ export class DatasetProfileEditorComponent extends BaseComponent implements OnIn
|
|||
|
||||
}
|
||||
|
||||
isStepCompleted(stepIndex: number){
|
||||
isStepCompleted(stepIndex: number){ //TODO NA TO DOUME MIPOS DEN XREIAZETAI
|
||||
|
||||
let stepCompleted = false;
|
||||
this.steps.forEach((step,index)=>{
|
||||
if(stepIndex === index){
|
||||
if(step.stepControl){
|
||||
stepCompleted = step.stepControl.valid;
|
||||
}
|
||||
stepCompleted = step.completed;
|
||||
}
|
||||
});
|
||||
|
||||
|
@ -1437,13 +1451,17 @@ export class DatasetProfileEditorComponent extends BaseComponent implements OnIn
|
|||
|
||||
isStepUnlocked(stepIndex: number): boolean{
|
||||
if(stepIndex === 0) return true;
|
||||
|
||||
if(stepIndex <0 ) return false;
|
||||
//if previous step is valid then unlock
|
||||
let stepUnlocked: boolean = false;
|
||||
|
||||
if(!this.isStepUnlocked(stepIndex -1)) return false;
|
||||
|
||||
this.steps.forEach((step,index)=>{
|
||||
|
||||
if(index+1 == stepIndex){//previous step
|
||||
if(step.stepControl.valid){
|
||||
|
||||
if(step.completed){
|
||||
stepUnlocked = true;
|
||||
}
|
||||
}
|
||||
|
@ -1453,27 +1471,27 @@ export class DatasetProfileEditorComponent extends BaseComponent implements OnIn
|
|||
}
|
||||
|
||||
validateStep(step: CdkStep){
|
||||
if(step.hasError){
|
||||
this.printMyErrors(this.form);
|
||||
}
|
||||
// if(step.hasError){
|
||||
// this.printMyErrors(this.form);
|
||||
// }
|
||||
}
|
||||
|
||||
getFormValidationErrors() {
|
||||
Object.keys(this.form.controls).forEach(key => {
|
||||
// getFormValidationErrors() {
|
||||
// Object.keys(this.form.controls).forEach(key => {
|
||||
|
||||
const controlErrors: ValidationErrors = this.form.get(key).errors;
|
||||
if (controlErrors != null) {
|
||||
Object.keys(controlErrors).forEach(keyError => {
|
||||
console.log('Key control: ' + key + ', keyError: ' + keyError + ', err value: ', controlErrors[keyError]);
|
||||
});
|
||||
}
|
||||
});
|
||||
// const controlErrors: ValidationErrors = this.form.get(key).errors;
|
||||
// if (controlErrors != null) {
|
||||
// Object.keys(controlErrors).forEach(keyError => {
|
||||
// console.log('Key control: ' + key + ', keyError: ' + keyError + ', err value: ', controlErrors[keyError]);
|
||||
// });
|
||||
// }
|
||||
// });
|
||||
|
||||
if(this.form.invalid){
|
||||
console.log('this form is invalid!');
|
||||
console.log(this.form.errors);
|
||||
}
|
||||
}
|
||||
// if(this.form.invalid){
|
||||
// console.log('this form is invalid!');
|
||||
// console.log(this.form.errors);
|
||||
// }
|
||||
// }
|
||||
|
||||
|
||||
|
||||
|
@ -1481,11 +1499,26 @@ export class DatasetProfileEditorComponent extends BaseComponent implements OnIn
|
|||
const errmess: string[] = [];
|
||||
|
||||
Object.keys(errors).forEach(keyError => {
|
||||
if (typeof errors[keyError] === 'boolean') {
|
||||
errmess.push(numbering + ' ' + key + ' is ' + keyError);
|
||||
} else {
|
||||
errmess.push(numbering + ' ' + key + ': ' + keyError + ': ' + JSON.stringify(errors[keyError]));
|
||||
|
||||
switch(keyError){
|
||||
case EditorCustomValidatorsEnum.atLeastOneSectionInPage:
|
||||
errmess.push('Each section must have at least one subsection');
|
||||
break;
|
||||
case EditorCustomValidatorsEnum.emptyArray:
|
||||
errmess.push(numbering+" needs more information.")
|
||||
break;
|
||||
case EditorCustomValidatorsEnum.sectionMustHaveOneChild:
|
||||
errmess.push(numbering+" must have either subsection or input sets.")
|
||||
break;
|
||||
default:
|
||||
if (typeof errors[keyError] === 'boolean') {
|
||||
errmess.push(numbering + ' ' + key + ' is ' + keyError);
|
||||
} else {
|
||||
errmess.push(numbering + ' ' + key + ': ' + keyError + ': ' + JSON.stringify(errors[keyError]));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
});
|
||||
|
||||
return errmess;
|
||||
|
@ -1495,59 +1528,67 @@ export class DatasetProfileEditorComponent extends BaseComponent implements OnIn
|
|||
printMyErrors(form: AbstractControl){
|
||||
// this._printToCentriesErrrors(this.toCEntries);
|
||||
const result = this._getErrors(form);
|
||||
// console.log('result', result);
|
||||
|
||||
|
||||
// console.log('got errors ');
|
||||
// console.log(result);
|
||||
|
||||
if(result){
|
||||
|
||||
form.markAllAsTouched();
|
||||
if(result && form.invalid){
|
||||
const errmess:string[] = [];
|
||||
if(result.length){
|
||||
form.markAllAsTouched();
|
||||
|
||||
let indexes:number[] = [];
|
||||
///search in pages,sections and fieldsets for the id
|
||||
result.forEach((err,i)=>{
|
||||
const entry = this._findTocEntryById(err.id, this.toCEntries);
|
||||
if(entry){
|
||||
let indexes:number[] = [];
|
||||
///search in pages,sections and fieldsets for the id
|
||||
result.forEach((err,i)=>{
|
||||
const entry = this._findTocEntryById(err.id, this.toCEntries);
|
||||
if(entry){
|
||||
|
||||
// errmess.push(`Error on ${entry.numbering} ${entry.label} . ${err.key}`);
|
||||
errmess.push(...this._buildErrorMessage(err.errors, entry.numbering, err.key));
|
||||
indexes.push(i);
|
||||
}
|
||||
});
|
||||
indexes.reverse().forEach(index=>{
|
||||
result.splice(index,1);
|
||||
});
|
||||
|
||||
indexes = [];
|
||||
//searching in fields
|
||||
const fieldsets = this._getAllFieldSets(this.toCEntries);
|
||||
result.forEach((err,i)=>{
|
||||
fieldsets.filter(fs=>{
|
||||
let fieldFound = false;
|
||||
(fs.form.get('fields') as FormArray).controls.forEach(field=>{
|
||||
if(field.get('id').value === err.id){
|
||||
fieldFound = true;
|
||||
indexes.push(i);
|
||||
}
|
||||
});
|
||||
return fieldFound;
|
||||
})
|
||||
//printing fieldsets that the field missing
|
||||
.forEach(fs=>{
|
||||
// errmess.push(`Missing input in ${fs.numbering} ${fs.label} . ${err.key}`);
|
||||
errmess.push(...this._buildErrorMessage(err.errors, fs.numbering, err.key));
|
||||
// errmess.push(`Error on ${entry.numbering} ${entry.label} . ${err.key}`);
|
||||
errmess.push(...this._buildErrorMessage(err.errors, entry.numbering, err.key));
|
||||
indexes.push(i);
|
||||
}
|
||||
});
|
||||
indexes.reverse().forEach(index=>{
|
||||
result.splice(index,1);
|
||||
});
|
||||
});
|
||||
|
||||
indexes.reverse().forEach(index=>{
|
||||
result.splice(index,1);
|
||||
});
|
||||
indexes = [];
|
||||
//searching in fields
|
||||
const fieldsets = this._getAllFieldSets(this.toCEntries);
|
||||
result.forEach((err,i)=>{
|
||||
fieldsets.filter(fs=>{
|
||||
let fieldFound = false;
|
||||
(fs.form.get('fields') as FormArray).controls.forEach(field=>{
|
||||
if(field.get('id').value === err.id){
|
||||
fieldFound = true;
|
||||
indexes.push(i);
|
||||
}
|
||||
});
|
||||
return fieldFound;
|
||||
})
|
||||
//printing fieldsets that the field missing
|
||||
.forEach(fs=>{
|
||||
// errmess.push(`Missing input in ${fs.numbering} ${fs.label} . ${err.key}`);
|
||||
errmess.push(...this._buildErrorMessage(err.errors, fs.numbering, err.key));
|
||||
});
|
||||
});
|
||||
|
||||
result.forEach(err=>{
|
||||
errmess.push(`Missing ${err.key}` );
|
||||
})
|
||||
indexes.reverse().forEach(index=>{
|
||||
result.splice(index,1);
|
||||
});
|
||||
|
||||
result.forEach(err=>{
|
||||
// console.log(err);
|
||||
if(err.key){
|
||||
errmess.push(`Missing ${err.key}` );
|
||||
}else{
|
||||
|
||||
errmess.push('Make sure you provide a section and a subsection');
|
||||
}
|
||||
// errmess.push(...this._buildErrorMessage(err.errors,"", err.key) );
|
||||
|
||||
})
|
||||
}
|
||||
|
||||
// console.log(result);
|
||||
|
||||
|
@ -1627,11 +1668,7 @@ export class DatasetProfileEditorComponent extends BaseComponent implements OnIn
|
|||
|
||||
private _getErrors(aControl: AbstractControl):InvalidControl[]{
|
||||
|
||||
// if(aControl instanceof FormGroup) console.log('is Formgroup');
|
||||
// if(aControl instanceof FormControl)console.log( aControl.errors);
|
||||
// if(aControl instanceof FormArray) console.log('isForm array');
|
||||
|
||||
// console
|
||||
if(aControl.valid) return;
|
||||
|
||||
let controlType = 'control';
|
||||
|
@ -1650,14 +1687,11 @@ export class DatasetProfileEditorComponent extends BaseComponent implements OnIn
|
|||
const keys = Object.keys(controls);
|
||||
keys.forEach(key=>{
|
||||
const control = controls[key];
|
||||
if(control.valid) return;
|
||||
if(!control.invalid) return; //// !!!!! Important to be !invalid. (In case the template is finalized)
|
||||
|
||||
if(control instanceof FormControl){
|
||||
const ctrl = control as FormControl;
|
||||
|
||||
// console.log('Control ', key,' of Formgroup ', aControl.get('id'), ' has errors', ctrl.errors);
|
||||
// console.log(aControl)
|
||||
|
||||
invalidControls.push({
|
||||
errors:ctrl.errors,
|
||||
id: ctrl.get('id')? ctrl.get('id').value: null,
|
||||
|
@ -1674,26 +1708,38 @@ export class DatasetProfileEditorComponent extends BaseComponent implements OnIn
|
|||
// invalidSubControls:[]//TODO TO CHECK
|
||||
// });
|
||||
// }
|
||||
if(control.errors){
|
||||
// invalidControls.push({
|
||||
// id: aControl.get('id')? aControl.get('id').value: null,
|
||||
// errors:aControl.errors,
|
||||
// key: aControl.get('title')? aControl.get('title').value: 'unspecified',
|
||||
// invalidSubControls:[]//TODO TO CHECK
|
||||
// });
|
||||
|
||||
invalidControls.push({
|
||||
errors:control.errors,
|
||||
id: control.get('id')? control.get('id').value: null,
|
||||
invalidSubControls: [],
|
||||
key: key
|
||||
});
|
||||
}
|
||||
|
||||
//THE ONE WE REMOVED
|
||||
// if(control.errors){
|
||||
// // invalidControls.push({
|
||||
// // id: aControl.get('id')? aControl.get('id').value: null,
|
||||
// // errors:aControl.errors,
|
||||
// // key: aControl.get('title')? aControl.get('title').value: 'unspecified',
|
||||
// // invalidSubControls:[]//TODO TO CHECK
|
||||
// // });
|
||||
|
||||
// invalidControls.push({
|
||||
// errors:control.errors,
|
||||
// id: control.get('id')? control.get('id').value: null,
|
||||
// invalidSubControls: [],
|
||||
// key: key
|
||||
// });
|
||||
// }
|
||||
invalidControls.push(...this._getErrors(control)) ;
|
||||
|
||||
}
|
||||
});
|
||||
|
||||
/**In case there is an error in a formgroup then the validator probably is custom */
|
||||
if(aControl.errors){
|
||||
invalidControls.push({
|
||||
errors:aControl.errors,
|
||||
id: aControl.get('id')? aControl.get('id').value: null,
|
||||
invalidSubControls: [],
|
||||
key: aControl.get('title')?aControl.get('title').value: null
|
||||
});
|
||||
}
|
||||
|
||||
break;
|
||||
case 'fa':
|
||||
|
|
|
@ -22,7 +22,7 @@
|
|||
|
||||
[ngStyle]="{'font-size' : (parentLink.type == tocEntryType.FieldSet? '.9rem':'1rem')}"
|
||||
> -->
|
||||
<span class="table-label-element" [ngClass]="{'table-label-element-active': itemSelected?.id == parentLink?.id}" (click)="itemClicked(parentLink)"
|
||||
<span class="table-label-element" [ngClass]="{'table-label-element-active': itemSelected?.id == parentLink?.id, 'text-danger': colorError()}" (click)="itemClicked(parentLink)"
|
||||
[ngStyle]="{'font-size' : (parentLink.type == tocEntryType.FieldSet? '.9rem':'1rem')}"
|
||||
>
|
||||
<!-- {{parentLink?.numbering}} {{parentLink?.label? parentLink?.label : 'DATASET-PROFILE-EDITOR.STEPS.GENERAL-INFO.UNTITLED' | translate}} -->
|
||||
|
@ -33,10 +33,14 @@
|
|||
|
||||
</div>
|
||||
<div class="col-auto d-flex align-items-center" >
|
||||
<span class="badge-ball"
|
||||
*ngIf="!(!((parentLink?.subEntriesType == tocEntryType.FieldSet) && !selectedItemInLinks) || itemSelected?.id == parentLink.id ||isDragging)">
|
||||
{{parentLink.subEntries?.length}}
|
||||
</span>
|
||||
|
||||
<ng-container *ngIf="!(!((parentLink?.subEntriesType == tocEntryType.FieldSet) && !selectedItemInLinks) || itemSelected?.id == parentLink.id ||isDragging)">
|
||||
<mat-icon class="text-danger" style="font-size: 1.4em;" *ngIf="!colorError() && parentLink?.form.invalid && colorizeInvalid && allFieldsAreTouched(parentLink?.form)">priority_high</mat-icon>
|
||||
<span class="badge-ball"
|
||||
>
|
||||
{{parentLink.subEntries?.length}}
|
||||
</span>
|
||||
</ng-container>
|
||||
|
||||
|
||||
<span style="cursor: pointer;" (click)="deleteEntry(parentLink)"
|
||||
|
@ -109,7 +113,8 @@
|
|||
[overContainerId]="overContainerId"
|
||||
[isDragging]="isDragging"
|
||||
[draggingItemId]="draggingItemId"
|
||||
[parentRootId]="parentRootId">
|
||||
[parentRootId]="parentRootId"
|
||||
[colorizeInvalid]="colorizeInvalid">
|
||||
</app-dataset-profile-table-of-contents-internal-section>
|
||||
|
||||
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
import { CdkDrag, CdkDragDrop, CdkDropList, moveItemInArray } from '@angular/cdk/drag-drop';
|
||||
import { DOCUMENT } from '@angular/common';
|
||||
import { Component, EventEmitter, Inject, Input, OnInit, Output, SimpleChanges, ViewChild } from '@angular/core';
|
||||
import { FormArray } from '@angular/forms';
|
||||
import { AbstractControl, FormArray, FormControl, FormGroup } from '@angular/forms';
|
||||
import { BaseComponent } from '@common/base/base.component';
|
||||
import { Foo, ToCEntry, ToCEntryType } from '../table-of-contents-entry';
|
||||
|
||||
|
@ -31,6 +31,8 @@ export class DatasetProfileTableOfContentsInternalSection extends BaseComponent
|
|||
@Input() draggingItemId: string;
|
||||
@Input() parentRootId: string;
|
||||
|
||||
@Input() colorizeInvalid:boolean = false;
|
||||
|
||||
@Input() viewOnly: boolean;
|
||||
// @Input() dropListGroup: Set<string> = new Set<string>();
|
||||
@Input() dropListGroup: string[];
|
||||
|
@ -229,4 +231,78 @@ export class DatasetProfileTableOfContentsInternalSection extends BaseComponent
|
|||
|
||||
return tocEntryFound? tocEntryFound: null;
|
||||
}
|
||||
|
||||
|
||||
|
||||
colorError():boolean{
|
||||
|
||||
if(!this.colorizeInvalid) return false;
|
||||
|
||||
const form = this.parentLink.form;
|
||||
if(!form || form.valid || !form.touched) return false;
|
||||
|
||||
const allFieldsAreTouched = this.allFieldsAreTouched(form);
|
||||
|
||||
//fieldset may have errros that are inside its controls and not in the fieldsetFormGroup
|
||||
if(this.parentLink.type === this.tocEntryType.FieldSet && allFieldsAreTouched) return true;
|
||||
|
||||
if(form.errors && allFieldsAreTouched) return true;
|
||||
|
||||
|
||||
|
||||
//checking form controls if have errors
|
||||
let hasErrors = false;
|
||||
|
||||
if(allFieldsAreTouched){
|
||||
if(form instanceof FormGroup){
|
||||
const formGroup = form as FormGroup;
|
||||
|
||||
const controls = Object.keys(formGroup.controls);
|
||||
|
||||
controls.forEach(control=>{
|
||||
if(formGroup.get(control).errors){
|
||||
hasErrors = true;
|
||||
}
|
||||
})
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
return hasErrors;
|
||||
}
|
||||
|
||||
|
||||
allFieldsAreTouched(aControl:AbstractControl){//auto na testaroume
|
||||
|
||||
if(!aControl|| aControl.untouched) return false;
|
||||
|
||||
if(aControl instanceof FormControl){
|
||||
return aControl.touched;
|
||||
}else if(aControl instanceof FormGroup){
|
||||
const controlKeys = Object.keys((aControl as FormGroup).controls);
|
||||
let areAllTouched = true;
|
||||
controlKeys.forEach(key=>{
|
||||
if(!this.allFieldsAreTouched(aControl.get(key))){
|
||||
areAllTouched = false;
|
||||
}
|
||||
})
|
||||
// const areAllTouched = controlKeys.reduce((acc, key)=>acc && this._allFieldsAreTouched(aControl.get(key)), true);
|
||||
return areAllTouched;
|
||||
|
||||
}else if(aControl instanceof FormArray){
|
||||
const controls = (aControl as FormArray).controls;
|
||||
// const areAllTouched = controls.reduce((acc, control)=>acc && this._allFieldsAreTouched(control), true);
|
||||
let areAllTouched = true;
|
||||
// controls.reduce((acc, control)=>acc && this._allFieldsAreTouched(control), true);
|
||||
controls.forEach(control=>{
|
||||
if(!this.allFieldsAreTouched(control)){
|
||||
areAllTouched = false;
|
||||
}
|
||||
});
|
||||
return areAllTouched;
|
||||
}
|
||||
|
||||
|
||||
return false;
|
||||
}
|
||||
}
|
|
@ -22,6 +22,7 @@
|
|||
[draggingItemId]="draggingItemId"
|
||||
[parentRootId]="ROOT_ID"
|
||||
style="padding-right: 1em;"
|
||||
[colorizeInvalid]="colorizeInvalid"
|
||||
></app-dataset-profile-table-of-contents-internal-section>
|
||||
|
||||
<!-- <span *ngFor="let link of links; let i = index" (click)="toggle(link); goToStep(link);" class="docs-link mt-0">
|
||||
|
|
|
@ -50,6 +50,7 @@ export class DatasetProfileTableOfContents extends BaseComponent implements OnIn
|
|||
@Output() dataNeedsRefresh = new EventEmitter<void>();
|
||||
|
||||
@Input() itemSelected: ToCEntry;
|
||||
@Input() colorizeInvalid: boolean = false;
|
||||
|
||||
// @Input() set itemSelected(entry:ToCEntry){
|
||||
// this._itemSelected = entry;
|
||||
|
|
|
@ -76,11 +76,11 @@
|
|||
}
|
||||
}
|
||||
|
||||
::ng-deep .mat-form-field-wrapper {
|
||||
:host ::ng-deep .mat-form-field-wrapper {
|
||||
background-color: white !important;
|
||||
padding-bottom: 0 !important;
|
||||
}
|
||||
|
||||
::ng-deep .mat-form-field-appearance-outline .mat-form-field-infix {
|
||||
:host ::ng-deep .mat-form-field-appearance-outline .mat-form-field-infix {
|
||||
padding: 0.3rem 0rem 0.6rem 0rem !important;
|
||||
}
|
||||
|
|
|
@ -10,11 +10,11 @@
|
|||
padding: 0.4rem;
|
||||
}
|
||||
|
||||
::ng-deep .mat-form-field-wrapper {
|
||||
:host ::ng-deep .mat-form-field-wrapper {
|
||||
background-color: white !important;
|
||||
padding-bottom: 0 !important;
|
||||
}
|
||||
|
||||
::ng-deep .mat-form-field-appearance-outline .mat-form-field-infix {
|
||||
:host ::ng-deep .mat-form-field-appearance-outline .mat-form-field-infix {
|
||||
padding: 0.3rem 0rem 0.6rem 0rem !important;
|
||||
}
|
||||
|
|
|
@ -122,7 +122,7 @@
|
|||
background-color: #2e74b649;
|
||||
}
|
||||
|
||||
::ng-deep .mat-form-field-wrapper {
|
||||
:host ::ng-deep .mat-form-field-wrapper {
|
||||
background-color: white !important;
|
||||
padding-bottom: 0 !important;
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue