import { Component, OnInit, Inject } from '@angular/core';
import { FormBuilder, FormGroup, Validators, FormArray } from '@angular/forms';
import { DirectorService, GENRES_DI } from './director.service';
import { Director, Movie, Genre } from './director';
import { map } from 'rxjs/operators';
@Component({
selector: 'app-director-form',
templateUrl: './director-form.component.html',
styles: [
` .form-group, .form-array { margin: 1em;}
label { display: inline-block; width: 200px}
.action-bar {
display: flex;
flex-direction: flex-row;
width: 360px;
flex-wrap: wrap;
justify-content: space-evenly
}
input + span {display: block; margin: 0; font-size: smaller; color: red}
.ng-invalid:not(form) {border-left: 5px solid red}`
],
providers: [{provide: GENRES_DI, useValue: Object.keys(Genre).filter(k => isNaN(Number(k)))}]
})
export class DirectorFormComponent implements OnInit {
directorForm: FormGroup;
length: number = 0;
constructor(
private fb: FormBuilder,
private service: DirectorService,
@Inject(GENRES_DI) private genres: string[]
) {
this.directorForm = this.createForm();
}
ngOnInit() {
this.setDataLength();
this.load();
}
setDataLength() {
this.service.getDirectors().pipe(map(data => data.length)).subscribe(size => this.length = size);
}
/**
* Randomly loads a director from data source.
*/
load() {
this.service.getDirector(this.getRandomId(this.length))
.subscribe(
(director) => this.directorForm.patchValue(this.getValueFrom(director)),
(err) => console.log(err)
);
}
/**
* Gets a random id.
* @param the max length of the data table.
*/
getRandomId(length: number): number {
let rd: number = Math.random() * 10 % length;
return Math.ceil(rd);
}
/**
* Creates the initial formGroup.
* @returns a formGroup instance
*/
createForm() {
return this.fb.group({
firstname: ['', Validators.required],
lastname: ['', Validators.required],
movies: this.fb.array([
])
});
}
/**
* Fills director's values.
*/
getValueFrom(author: Director) {
let value = {firstname: '',lastname: ''};
this.resetMovies();// reset to avoid duplicates after loading
for (let key in author) {
if (this.directorForm.get(key)) {
if (Array.isArray(author[key])) {
author[key].forEach(m => this.setMovie(m))
} else {
value[key] = author[key];
}
}
}
return value;
}
// GETTERS
get firstname() {
return this.directorForm.get('firstname');
}
get lastname() {
return this.directorForm.get('lastname');
}
/**
* Gets the movies' formArray.
* @returns movies formControl as FormArray
*/
get movies() {
return this.directorForm.get('movies') as FormArray;
}
/**
* Adds a new group {[title]: string, [genre]: string} to the movies' formArray of the director.
* @param some movie instance
*/
setMovie(movie: Movie) {
this.movies.push(this.fb.group({ title: movie.title, genre: movie.genre }));
}
addMovie() {
this.movies.push(this.fb.group({ title: '', genre: '' }));
}
removeMovie(index: number) {
this.movies.removeAt(index);
}
/**
* Clears the formArray modelling this director's movies.
*/
resetMovies() {
while (this.movies.length > 0) {
this.movies.removeAt(0);
}
}
onSubmit(formValue: any) {
console.log(formValue);
}
}