table of contents error indicator
This commit is contained in:
parent
3ec12fdf59
commit
79817e63e0
|
@ -41,3 +41,9 @@
|
|||
border: 0px;
|
||||
}
|
||||
}
|
||||
|
||||
::ng-deep .mdc-form-field {
|
||||
label {
|
||||
margin: 0;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -93,7 +93,7 @@
|
|||
<div (click)="table0fContents.onToCentrySelected()" *ngIf="descriptionInfoValid()" class="main-info" [ngClass]="{'active': this.step === 0}">0. {{'DESCRIPTION-EDITOR.TOC.MAIN-INFO' | translate}} (<mat-icon class="done-icon">done</mat-icon>)</div>
|
||||
<div class="row toc-pane-container" #boundary>
|
||||
<div #spacer></div>
|
||||
<app-table-of-contents [visibilityRulesService]="visibilityRulesService" [selectedFieldsetId]="fieldsetIdWithFocus" #table0fContents [showErrors]="showtocentriesErrors" [TOCENTRY_ID_PREFIX]="TOCENTRY_ID_PREFIX" [hasFocus]="step > 0" [propertiesFormGroup]="formGroup.get('properties')" [descriptionTemplate]="item.descriptionTemplate" *ngIf="formGroup" [links]="links" [boundary]="boundary" [spacer]="spacer" [isActive]="step !== 0" stickyThing (stepFound)="onStepFound($event)" (currentLinks)="getLinks($event)" (entrySelected)="changeStep($event.entry, $event.execute)"></app-table-of-contents>
|
||||
<app-table-of-contents [visibilityRulesService]="visibilityRulesService" [selectedFieldsetId]="fieldsetIdWithFocus" #table0fContents [showErrors]="showtocentriesErrors" [TOCENTRY_ID_PREFIX]="TOCENTRY_ID_PREFIX" [hasFocus]="step > 0" [formGroup]="formGroup.get('properties')" [descriptionTemplate]="item.descriptionTemplate" *ngIf="formGroup" [links]="links" [boundary]="boundary" [spacer]="spacer" [isActive]="step !== 0" stickyThing (stepFound)="onStepFound($event)" (currentLinks)="getLinks($event)" (entrySelected)="changeStep($event.entry, $event.execute)" [pageToFieldSetMap]="pageToFieldSetMap"></app-table-of-contents>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
|
|
@ -6,7 +6,7 @@ import { DescriptionStatus } from '@app/core/common/enum/description-status';
|
|||
import { DmpStatus } from '@app/core/common/enum/dmp-status';
|
||||
import { IsActive } from '@app/core/common/enum/is-active.enum';
|
||||
import { AppPermission } from '@app/core/common/enum/permission.enum';
|
||||
import { Description, DescriptionPersist, DescriptionSectionPermissionResolver, DescriptionStatusPersist } from '@app/core/model/description/description';
|
||||
import { Description, DescriptionPersist, DescriptionPropertyDefinitionFieldSet, DescriptionSectionPermissionResolver, DescriptionStatusPersist } from '@app/core/model/description/description';
|
||||
import { AuthService } from '@app/core/services/auth/auth.service';
|
||||
import { DescriptionTemplateService } from '@app/core/services/description-template/description-template.service';
|
||||
import { DescriptionService } from '@app/core/services/description/description.service';
|
||||
|
@ -32,7 +32,7 @@ import { FilterService } from '@common/modules/text-filter/filter-service';
|
|||
import { Guid } from '@common/types/guid';
|
||||
import { TranslateService } from '@ngx-translate/core';
|
||||
import { map, takeUntil } from 'rxjs/operators';
|
||||
import { DescriptionEditorModel, DescriptionPropertyDefinitionEditorModel } from './description-editor.model';
|
||||
import { DescriptionEditorModel, DescriptionFieldIndicator, DescriptionPropertyDefinitionEditorModel } from './description-editor.model';
|
||||
import { DescriptionEditorResolver } from './description-editor.resolver';
|
||||
import { DescriptionEditorService } from './description-editor.service';
|
||||
import { PrefillDescriptionDialogComponent } from './prefill-description/prefill-description.component';
|
||||
|
@ -44,8 +44,11 @@ import { ConfigurationService } from '@app/core/services/configuration/configura
|
|||
import { LockTargetType } from '@app/core/common/enum/lock-target-type';
|
||||
import { FileTransformerService } from '@app/core/services/file-transformer/file-transformer.service';
|
||||
import { DmpBlueprintDefinitionSection } from '@app/core/model/dmp-blueprint/dmp-blueprint';
|
||||
import { DescriptionTemplate } from '@app/core/model/description-template/description-template';
|
||||
import { DescriptionTemplate, DescriptionTemplateField, DescriptionTemplateFieldSet, DescriptionTemplatePage, DescriptionTemplateSection } from '@app/core/model/description-template/description-template';
|
||||
import { DmpDescriptionTemplate } from '@app/core/model/dmp/dmp';
|
||||
import { BehaviorSubject } from 'rxjs';
|
||||
import { UUID } from 'crypto';
|
||||
import { AbstractControl } from '@angular/forms';
|
||||
|
||||
@Component({
|
||||
selector: 'app-description-editor-component',
|
||||
|
@ -67,6 +70,7 @@ export class DescriptionEditorComponent extends BaseEditor<DescriptionEditorMode
|
|||
@ViewChild('table0fContents') table0fContents: TableOfContentsComponent;
|
||||
step: number = 0;
|
||||
|
||||
pageToFieldSetMap: Map<string, DescriptionFieldIndicator[]> = new Map<string, DescriptionFieldIndicator[]>();
|
||||
|
||||
constructor(
|
||||
// BaseFormEditor injected dependencies
|
||||
|
@ -205,8 +209,8 @@ export class DescriptionEditorComponent extends BaseEditor<DescriptionEditorMode
|
|||
|
||||
const sectionId = this.item.dmpDescriptionTemplate.sectionId;
|
||||
result.dmpDescriptionTemplate = this.item.dmp.dmpDescriptionTemplates.find(x => x.sectionId == sectionId && x.descriptionTemplateGroupId == result.descriptionTemplate.groupId);
|
||||
|
||||
this.prepareForm(result);
|
||||
|
||||
// this.descriptionModel = this.descriptionModel.fromModel(result);
|
||||
// this.descriptionModel.dmp = data;
|
||||
// this.descriptionModel.dmpSectionIndex = this.dmpSectionIndex;
|
||||
|
@ -848,6 +852,10 @@ export class DescriptionEditorComponent extends BaseEditor<DescriptionEditorMode
|
|||
// this.formChanged();
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
this.checkPagesForErrors();
|
||||
|
||||
// // const labelSubscription =
|
||||
// this.formGroup.get('label').valueChanges
|
||||
// .pipe(takeUntil(this._destroyed))
|
||||
|
@ -903,6 +911,38 @@ export class DescriptionEditorComponent extends BaseEditor<DescriptionEditorMode
|
|||
}
|
||||
}
|
||||
|
||||
checkPagesForErrors(): void {
|
||||
this.pageToFieldSetMap = this.mapPageToFieldSet(this.item.descriptionTemplate);
|
||||
}
|
||||
|
||||
mapPageToFieldSet(descriptionTemplate: DescriptionTemplate): Map<string, DescriptionFieldIndicator[]> {
|
||||
const pageToFieldSetMap = new Map<string, DescriptionFieldIndicator[]>();
|
||||
|
||||
descriptionTemplate.definition.pages?.forEach((page: DescriptionTemplatePage) => {
|
||||
page.sections?.forEach((section: DescriptionTemplateSection) => {
|
||||
const fieldsets = this.getFieldsetsFromSection(section);
|
||||
const value = fieldsets?.flatMap((fieldset: DescriptionTemplateFieldSet) =>
|
||||
fieldset.fields?.flatMap((field: DescriptionTemplateField) =>
|
||||
new DescriptionFieldIndicator(page.id, section.id, fieldset.id, field.id, field.data.fieldType, field.data.multipleSelect)
|
||||
// 'properties.fieldSets.' + fieldset.id + '.items.0.fields.' + field.id// + '.textValue'
|
||||
));
|
||||
pageToFieldSetMap.set(page.id,
|
||||
value
|
||||
);
|
||||
});
|
||||
});
|
||||
|
||||
return pageToFieldSetMap;
|
||||
}
|
||||
|
||||
getFieldsetsFromSection(section: DescriptionTemplateSection): DescriptionTemplateFieldSet[] {
|
||||
if (section.sections) {
|
||||
return section.sections.flatMap((subsection: DescriptionTemplateSection) => this.getFieldsetsFromSection(subsection));
|
||||
}
|
||||
|
||||
else return section.fieldSets;
|
||||
}
|
||||
|
||||
// // this._listenersSubscription.add(dmpSubscription);
|
||||
// // this._listenersSubscription.add(profileSubscription);
|
||||
// // this._listenersSubscription.add(labelSubscription);
|
||||
|
|
|
@ -1,5 +1,6 @@
|
|||
import { FormControl, UntypedFormArray, UntypedFormBuilder, UntypedFormGroup, Validators } from "@angular/forms";
|
||||
import { DescriptionStatus } from "@app/core/common/enum/description-status";
|
||||
import { DescriptionTemplateFieldType } from "@app/core/common/enum/description-template-field-type";
|
||||
import { IsActive } from "@app/core/common/enum/is-active.enum";
|
||||
import { DescriptionTemplate, DescriptionTemplateField, DescriptionTemplateFieldSet, DescriptionTemplateSection } from "@app/core/model/description-template/description-template";
|
||||
import { Description, DescriptionExternalIdentifier, DescriptionExternalIdentifierPersist, DescriptionField, DescriptionFieldPersist, DescriptionPersist, DescriptionPropertyDefinition, DescriptionPropertyDefinitionFieldSet, DescriptionPropertyDefinitionFieldSetItem, DescriptionPropertyDefinitionFieldSetItemPersist, DescriptionPropertyDefinitionFieldSetPersist, DescriptionPropertyDefinitionPersist, DescriptionReference, DescriptionReferencePersist } from "@app/core/model/description/description";
|
||||
|
@ -672,3 +673,59 @@ export class DescriptionReferenceEditorModel implements DescriptionReferencePers
|
|||
});
|
||||
}
|
||||
}
|
||||
|
||||
export class DescriptionFieldIndicator {
|
||||
pageId: string;
|
||||
sectionId: string;
|
||||
fieldSetId: string;
|
||||
fieldId: string;
|
||||
type: string;
|
||||
|
||||
constructor(pageId: string, sectionId: string, fieldSetId: string, fieldId: string, type: DescriptionTemplateFieldType, multipleSelect: boolean = false) {
|
||||
this.pageId = pageId;
|
||||
this.sectionId = sectionId;
|
||||
this.fieldSetId = fieldSetId;
|
||||
this.fieldId = fieldId;
|
||||
|
||||
switch (type) {
|
||||
case DescriptionTemplateFieldType.FREE_TEXT:
|
||||
case DescriptionTemplateFieldType.BOOLEAN_DECISION:
|
||||
case DescriptionTemplateFieldType.CHECK_BOX:
|
||||
case DescriptionTemplateFieldType.RADIO_BOX:
|
||||
case DescriptionTemplateFieldType.TEXT_AREA:
|
||||
case DescriptionTemplateFieldType.UPLOAD:
|
||||
case DescriptionTemplateFieldType.RICH_TEXT_AREA:
|
||||
this.type = "textValue";
|
||||
break;
|
||||
case DescriptionTemplateFieldType.DATASET_IDENTIFIER:
|
||||
case DescriptionTemplateFieldType.VALIDATION:
|
||||
this.type = "externalIdentifier";
|
||||
break;
|
||||
case DescriptionTemplateFieldType.DATE_PICKER:
|
||||
this.type = "dateValue";
|
||||
break;
|
||||
case DescriptionTemplateFieldType.EXTERNAL_DATASETS:
|
||||
this.type = "";
|
||||
break;
|
||||
case DescriptionTemplateFieldType.INTERNAL_ENTRIES_DESCRIPTIONS:
|
||||
if (multipleSelect) this.type = "textListValue";
|
||||
else this.type = "textValue"
|
||||
break;
|
||||
case DescriptionTemplateFieldType.INTERNAL_ENTRIES_DMPS:
|
||||
if (multipleSelect) this.type = "textListValue";
|
||||
else this.type = "textValue";
|
||||
break;
|
||||
case DescriptionTemplateFieldType.REFERENCE_TYPES:
|
||||
if (multipleSelect) this.type = "references";
|
||||
else this.type = "reference";
|
||||
break;
|
||||
case DescriptionTemplateFieldType.SELECT:
|
||||
if (multipleSelect) this.type = "textListValue";
|
||||
else this.type = "textValue";
|
||||
break;
|
||||
case DescriptionTemplateFieldType.TAGS:
|
||||
this.type = "textListValue";
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -39,6 +39,9 @@
|
|||
[showErrors]="showErrors"
|
||||
[hiddenEntries]="hiddenEntries"
|
||||
[visibilityRulesService]="visibilityRulesService"
|
||||
[propertiesFormGroup]="propertiesFormGroup"
|
||||
[parentId]="entry.id"
|
||||
[parentMap]="updatedMap"
|
||||
>
|
||||
|
||||
</table-of-contents-internal>
|
||||
|
|
|
@ -22,8 +22,9 @@
|
|||
background-color: #ececec;
|
||||
border-radius: 6px;
|
||||
}
|
||||
|
||||
.selected {
|
||||
color: #212121 !important;
|
||||
color: #212121;
|
||||
font-weight: 700 !important;
|
||||
opacity: 1 !important;
|
||||
}
|
||||
|
|
|
@ -4,6 +4,7 @@ import { VisibilityRulesService } from '@app/ui/description/editor/description-f
|
|||
import { Guid } from '@common/types/guid';
|
||||
import { ToCEntry } from '../models/toc-entry';
|
||||
import { ToCEntryType } from '../models/toc-entry-type.enum';
|
||||
import { DescriptionFieldIndicator } from '../../description-editor.model';
|
||||
|
||||
@Component({
|
||||
selector: 'table-of-contents-internal',
|
||||
|
@ -26,6 +27,10 @@ export class TableOfContentsInternal implements OnInit {
|
|||
@Input() visibilityRulesService: VisibilityRulesService;
|
||||
@ViewChildren(TableOfContentsInternal) internalTables: QueryList<TableOfContentsInternal>;
|
||||
|
||||
@Input() parentId: string;
|
||||
@Input() parentMap: Map<string, DescriptionFieldIndicator[]> = new Map<string, DescriptionFieldIndicator[]>();
|
||||
@Input() updatedMap: Map<string, DescriptionFieldIndicator[]> = new Map<string, DescriptionFieldIndicator[]>();
|
||||
|
||||
constructor() {
|
||||
}
|
||||
ngOnInit(): void {
|
||||
|
@ -42,6 +47,11 @@ export class TableOfContentsInternal implements OnInit {
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (this.parentMap) {
|
||||
this.updatedMap = this.updateMap(this.tocentries, this.parentMap);
|
||||
console.log(this.updatedMap);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -64,6 +74,47 @@ export class TableOfContentsInternal implements OnInit {
|
|||
// }
|
||||
}
|
||||
|
||||
updateMap(entries: ToCEntry[], parentMap:Map<string, DescriptionFieldIndicator[]>): Map<string, DescriptionFieldIndicator[]> {
|
||||
if (this.parentId == null) return parentMap;
|
||||
|
||||
let updatedMap = new Map<string, DescriptionFieldIndicator[]>();
|
||||
|
||||
parentMap.forEach((fields: DescriptionFieldIndicator[], parentId: string) => {
|
||||
if (this.parentId === parentId) {
|
||||
for (let entry of entries) {
|
||||
let entryFields = fields.filter((field: DescriptionFieldIndicator) => field.sectionId === entry.id || field.fieldSetId === entry.id || field.fieldId === entry.id )
|
||||
|
||||
updatedMap.set(entry.id, entryFields);
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
return updatedMap;
|
||||
}
|
||||
|
||||
hasErrors(entryId: string): boolean {
|
||||
if (this.updatedMap.size == 0) return true;
|
||||
|
||||
const fields: DescriptionFieldIndicator[] = this.updatedMap.get(entryId);
|
||||
|
||||
for (let field of fields) {
|
||||
let formFieldName: string = `fieldSets.${field.fieldSetId}.items.0.fields.${field.fieldId}.${field.type}`;
|
||||
if (this.isFormFieldValid(formFieldName) === false) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
isFormFieldValid(formFildName: string):boolean {
|
||||
if (this.propertiesFormGroup?.get(formFildName) == null) return true;
|
||||
|
||||
if (this.propertiesFormGroup.get(formFildName).touched === false) return true;
|
||||
|
||||
return this.propertiesFormGroup.get(formFildName).valid;
|
||||
}
|
||||
|
||||
toggleExpand(index) {
|
||||
this.expandChildren[index] = !this.expandChildren[index];
|
||||
// console.log(this.expandChildren);
|
||||
|
@ -113,6 +164,9 @@ export class TableOfContentsInternal implements OnInit {
|
|||
myClass['section'] = true;
|
||||
}
|
||||
|
||||
if(this.hasErrors(entry.id)) {
|
||||
myClass['text-danger'] = true;
|
||||
}
|
||||
return myClass;
|
||||
}
|
||||
|
||||
|
|
|
@ -15,7 +15,8 @@
|
|||
[selected]="tocentrySelected"
|
||||
[hiddenEntries]="hiddenEntries"
|
||||
[visibilityRulesService]="visibilityRulesService"
|
||||
[propertiesFormGroup]="propertiesFormGroup"
|
||||
[propertiesFormGroup]="formGroup"
|
||||
[parentMap]="pageToFieldSetMap"
|
||||
>
|
||||
|
||||
</table-of-contents-internal>
|
||||
|
|
|
@ -9,6 +9,7 @@ import { debounceTime, distinctUntilChanged, takeUntil } from 'rxjs/operators';
|
|||
import { ToCEntry } from './models/toc-entry';
|
||||
import { ToCEntryType } from './models/toc-entry-type.enum';
|
||||
import { TableOfContentsInternal } from './table-of-contents-internal/table-of-contents-internal';
|
||||
import { DescriptionFieldIndicator } from '../description-editor.model';
|
||||
|
||||
export interface Link {
|
||||
/* id of the section*/
|
||||
|
@ -65,12 +66,14 @@ export class TableOfContentsComponent extends BaseComponent implements OnInit, O
|
|||
this._tocentrySelected = value;
|
||||
}
|
||||
|
||||
@Input() propertiesFormGroup: UntypedFormGroup;
|
||||
@Input() formGroup: UntypedFormGroup;
|
||||
@Input() descriptionTemplate: DescriptionTemplate;
|
||||
@Input() hasFocus: boolean = false;
|
||||
@Input() visibilityRulesService: VisibilityRulesService;
|
||||
show: boolean = false;
|
||||
|
||||
@Input() pageToFieldSetMap: Map<string, DescriptionFieldIndicator[]>;
|
||||
|
||||
constructor(
|
||||
@Inject(DOCUMENT) private _document: Document,
|
||||
// public visibilityRulesService: VisibilityRulesService
|
||||
|
|
Loading…
Reference in New Issue