import { ReplaySubject } from 'rxjs/index';
import { BsModalRef } from 'ngx-bootstrap/modal';
import { RCUSTATUSES } from 'Helpers/rcustatuses';
import { FormGroup, FormBuilder, FormArray } from '@angular/forms';
import { ModalDirective } from 'ngx-bootstrap/modal/modal.directive';
import { AuthUserService } from 'Services/auth-user.service';
import { finalize, distinctUntilChanged, debounceTime, } from 'rxjs/operators';
import { Component, OnInit, OnChanges, Input, ViewChild, SimpleChanges } from '@angular/core';
import { RelocationChecklistService } from 'AppService/service/relocation-checklist.service';
import { RelocationChecklistStatusService } from 'AppMscCompliance/services/relocation-checklist-status.service';
@Component({
selector: 'v-relocation-internal-checklist',
templateUrl: './relocation-internal-checklist.component.html',
styleUrls: [ './relocation-internal-checklist.component.scss' ],
})
export class RelocationInternalChecklistComponent implements OnInit, OnChanges {
modalRef: BsModalRef;
@ViewChild('modal') modal: ModalDirective;
@Input()
rcu_case_id: number = null;
@Input()
status_name: string = '';
@Input()
existing_checklists: any[] = null;
checklistForm: FormGroup;
onChanges = new ReplaySubject<SimpleChanges>();
checklist_items = [
{
id: 2,
name: 'Renting: Stamp certified true copy of tenancy agreement.'
},
{
id: 3,
name: 'Own premise: Stamp certified true copy of Sales & Purchase Agreement'
},
{
id: 4,
name: 'Office Space in Sq.Ft'
},
];
state = {
can_update: false,
};
meta = {
is_loading: false
};
constructor(
public authUser: AuthUserService,
private relocationChecklistService: RelocationChecklistService,
private relocationChecklistStatusService: RelocationChecklistStatusService,
private fb: FormBuilder
) {
}
ngOnInit(): void {
this.checklistForm = this.fb.group({
checklists: this.buildChecklist()
});
// set existing item only when input existing_checklists data is ready
this.onChanges.subscribe(data => {
this.setExistingItem(this.existing_checklists);
});
// listen for checkbox item changes
this.itemChanges();
}
ngOnChanges(changes: SimpleChanges) {
if (changes['rcu_case_id'] && this.rcu_case_id) {
console.log('checklist rcu_case_id', this.rcu_case_id);
}
if (changes['status_name'] && this.status_name) {
// reset the state
this.state = {
can_update: false,
};
this.enableUpdateChecklist(this.status_name);
}
if (changes['existing_checklists'] && this.existing_checklists) {
console.log('existing_checklists', this.existing_checklists);
this.onChanges.next(changes);
}
}
// first build of checkbox
buildChecklist() {
const controls = this.checklist_items.map(item => this.fb.control(false));
return this.fb.array(controls);
}
// enable update checklist
private enableUpdateChecklist(status_name: string) {
if (
status_name === RCUSTATUSES.IN_PROGRESS
|| status_name === RCUSTATUSES.RESUBMITTED
) {
this.state.can_update = true;
}
}
// getter
get formData() { return <FormArray> this.checklistForm.get('checklists'); }
// rebuild checkbox after received pre-checked data from API
rebuildChecklist(selected_ids: number[]) {
const controls = [];
for(let i = 0; i < this.checklist_items.length; i++) {
let checked = false;
if (selected_ids.indexOf(this.checklist_items[i].id) !== -1) {
checked = true;
}
const form_state = {
value: checked,
disabled: !this.state.can_update
};
controls.push(this.fb.control(form_state));
}
return this.fb.array(controls);
}
// when user check / uncheck item, auto store via API
itemChanges(): void {
this.checklistForm.valueChanges
.pipe(
debounceTime(400),
distinctUntilChanged()
)
.subscribe(value => {
const selectedItemIds = this.getSelectedItems();
console.log(selectedItemIds);
this.storeChecklist(selectedItemIds);
this.enableApproveRelocation(selectedItemIds);
});
}
// enable Approve if user checked all the items
enableApproveRelocation(selectedItemIds) {
const checklist_item_ids = this.checklist_items.map(function (item) {
return item.id;
});
const item_diff = this.arr_diff(selectedItemIds, checklist_item_ids);
if (item_diff.length === 0) {
this.relocationChecklistStatusService.changeStatus(true);
} else {
this.relocationChecklistStatusService.changeStatus(false);
}
}
// get latest checked items id
getSelectedItems() {
const selectedItemIds = this.checklistForm.value.checklists
.map((v, i) => v ? this.checklist_items[i].id : null)
.filter(v => v !== null);
return selectedItemIds;
}
// from API checklists, extract the item id
getExistingSelectedItemIds(checklist_items) {
const existing_checklist_item_ids = checklist_items.map(item => item.pivot.checklist_item_id);
console.log('existing_checklist_item_ids', existing_checklist_item_ids);
return existing_checklist_item_ids;
}
// pre-selected existing checklist
setExistingItem(existing_checklists) {
const selected_ids = this.getExistingSelectedItemIds(existing_checklists);
console.log('selected_ids', selected_ids);
this.checklistForm.setControl('checklists', this.rebuildChecklist(selected_ids) );
this.enableApproveRelocation(selected_ids);
}
// store latest checklist item
storeChecklist(items) {
if (!this.state.can_update) {
return false;
}
this.meta.is_loading = true;
this.relocationChecklistService.syncItems(this.rcu_case_id, items)
.pipe(finalize(() => this.meta.is_loading = false ))
.subscribe(
res => {
console.log(res);
},
err => {
console.log('err', err);
});
}
arr_diff(a1, a2) {
const a = [], diff = [];
for (let i = 0; i < a1.length; i++) {
a[a1[i]] = true;
}
for (let i = 0; i < a2.length; i++) {
if (a[a2[i]]) {
delete a[a2[i]];
} else {
a[a2[i]] = true;
}
}
for (const k in a) {
diff.push(k);
}
return diff;
}
}