import { Category } from './../../../../shared/models/category.interface'; import { Component, Input, OnInit } from '@angular/core'; import { FormBuilder, Validators, FormGroup } from '@angular/forms'; import { DocumentClassification } from 'src/app/shared/models/document-classification.interface'; import { CategoriesService } from 'src/app/shared/services/administration/categories.service'; import { DocumentClassificationsService } from 'src/app/shared/services/administration/document-classifications.service'; import { ErrorHandlingService } from 'src/app/shared/services/error-handling/error-handling.service'; @Component({ selector: 'app-category-form', templateUrl: './category-form.component.html', styleUrls: ['./category-form.component.scss'] }) export class CategoryFormComponent implements OnInit { /* * Inputs */ @Input() dialogLayout: boolean = false; // Controls .scss classes to allow for better dispay in a dialog. @Input() requiredFields: string[] | boolean = false; // True/False indicates that all/none are required. String[] specifies the form controls required. @Input() displayValidationMessagesEvenIfPristine: boolean = false; // Serves for manually treating the controls as dirty. @Input() autosuggestInputs: boolean = false; /* * Reactive Form */ categoryForm = this.fb.group({ documentClassification: [null], categoryName: [null], categoryCode: [null] }); setFormValue: Category = null; selectedCategory: Category; /* * Other Variables */ documentClassificationsList: DocumentClassification[]; categoryNameSuggestions: string[]; categoryCodeSuggestions: string[]; categorySuggestions: Category[]; /* * Constructor & Initialisers */ constructor( private fb: FormBuilder, private categoriesService: CategoriesService, private documentClassificationsService: DocumentClassificationsService, private errorHandlingService: ErrorHandlingService ) { } ngOnInit(): void { this.initData(); this.initValidators() } initData() { this.documentClassificationsService.getAll().subscribe( value => this.documentClassificationsList = value, err => this.errorHandlingService.showHttpResponseError(err) ); } // TODO: Have this mechanism offer the use of custom validators too. initValidators() { if (!this.requiredFields) { return; } // In a true/false case. if (typeof this.requiredFields == 'boolean') { // If true, enable the required validator for all controls and sub-controls. if (this.requiredFields) { this.setRequiredValidatorRecursively(this.categoryForm); } // If false, do nothing. return; } // If it was a string array, enable the validators for all provided field-names. TODO: This ONLY supports 1st level controls and not nested ones. (this.requiredFields).forEach(field => this.categoryForm.controls[field].setValidators(Validators.required)) } setRequiredValidatorRecursively(group: FormGroup) { Object.keys(group.controls).forEach(key => { group.controls[key].setValidators(Validators.required); if (group.controls[key]['controls']) { this.setRequiredValidatorRecursively(group.controls[key]) } }); } /* * Auto-suggest & Auto-complete Category */ autosuggestCategoryName(event) { if (!event.query || event.query.length < 3) { this.categoryNameSuggestions = []; return; } let classId = this.categoryForm.get('documentClassification').value ? this.categoryForm.get('documentClassification').value.classificationId : null; this.categoriesService.autosuggestCategoryName(event.query, classId).subscribe( (values: Category[]) => { let temp: string[] = []; this.categorySuggestions = values; values.map(val => temp.push(val.categoryName)); this.categoryNameSuggestions = temp }, err => this.errorHandlingService.showHttpResponseError(err) ); } autosuggestCategoryCode(event) { if (event.query.length < 3) { this.categoryCodeSuggestions = []; return; } let classId = this.categoryForm.get('documentClassification').value ? this.categoryForm.get('documentClassification').value.classificationId : null; this.categoriesService.autosuggestCategoryCode(event.query, classId).subscribe( (values: Category[]) => { let temp: string[] = []; this.categorySuggestions = values; values.map(val => temp.push(val.categoryCode)); this.categoryCodeSuggestions = temp }, err => this.errorHandlingService.showHttpResponseError(err) ); } categoryNameSelected(name: string) { this.selectedCategory = this.categorySuggestions.find(cat => cat.categoryName == name); this.categoryForm.get('categoryCode').patchValue(this.selectedCategory.categoryCode); this.categoryForm.updateValueAndValidity(); } categoryCodeSelected(code: string) { this.selectedCategory = this.categorySuggestions.find(cat => cat.categoryCode == code); this.categoryForm.get('categoryName').patchValue(this.selectedCategory.categoryName); this.categoryForm.updateValueAndValidity(); } /* * API methods */ public resetForm(): void { this.categoryForm.reset(); } public formValue(): Category { let formValue: Category = { id: this.setFormValue ? this.setFormValue.id : null, documentClassification: this.categoryForm.get('documentClassification').value, categoryName: this.categoryForm.get('categoryName').value, categoryCode: this.categoryForm.get('categoryCode').value }; return formValue; } public setValue(value: Category): void { if (!value) { return; } this.setFormValue = value; this.categoryForm.get('documentClassification').setValue(value.documentClassification); this.categoryForm.get('categoryName').setValue(value.categoryName); this.categoryForm.get('categoryCode').setValue(value.categoryCode); this.categoryForm.updateValueAndValidity(); } public isValid(): boolean { return this.categoryForm.valid; } }