@@ -0,0 +1,69 @@
|
||||
<div class="mat-typography">
|
||||
|
||||
<h3>Address</h3>
|
||||
|
||||
<div fxLayout="row" fxLayoutAlign="flex-end" class="m-b-20">
|
||||
<button mat-raised-button color="primary" (click)="addAddress()">
|
||||
<fa-icon icon="plus"></fa-icon> Add
|
||||
</button>
|
||||
</div>
|
||||
|
||||
<mat-accordion>
|
||||
|
||||
<mat-expansion-panel *ngFor="let address of clientAddressData; index as i" class="address">
|
||||
|
||||
<mat-expansion-panel-header>
|
||||
|
||||
<mat-panel-title>
|
||||
{{ getSelectedValue('addressTypeIdOptions',address.addressTypeId)?.name }}
|
||||
</mat-panel-title>
|
||||
|
||||
<mat-panel-description>
|
||||
{{ address.relationship }}
|
||||
</mat-panel-description>
|
||||
|
||||
</mat-expansion-panel-header>
|
||||
|
||||
<mat-divider></mat-divider>
|
||||
|
||||
<div class="address-actions" fxLayout="row" fxLayoutAlign="flex-end center">
|
||||
<button mat-button color="primary" (click)="editAddress(address,i)">
|
||||
<fa-icon icon="edit"></fa-icon>
|
||||
</button>
|
||||
<button mat-button color="warn" (click)="deleteAddress(address,i)">
|
||||
<fa-icon icon="trash"></fa-icon>
|
||||
</button>
|
||||
<mat-slide-toggle [checked]="address.isActive" (change)="toggleAddress(address)"></mat-slide-toggle>
|
||||
</div>
|
||||
|
||||
<p>
|
||||
<span *ngIf="isFieldEnabled('street')">Street : {{address.street}}<br /></span>
|
||||
<span *ngIf="isFieldEnabled('addressLine1')">Address Line 1 : {{address.addressLine1}}<br /></span>
|
||||
<span *ngIf="isFieldEnabled('addressLine2')">Address Line 2 : {{address.addressLine2}}<br /></span>
|
||||
<span *ngIf="isFieldEnabled('addressLine3')">Address Line 3 : {{address.addressLine3}}<br /></span>
|
||||
<span *ngIf="isFieldEnabled('townVillage')">Town / Village : {{address.townVillage}}<br /></span>
|
||||
<span *ngIf="isFieldEnabled('city')">City : {{address.city}}<br /></span>
|
||||
<span *ngIf="isFieldEnabled('stateProvinceId')">State / Province :
|
||||
{{getSelectedValue('stateProvinceIdOptions',address.stateProvinceId)?.name}}<br /></span>
|
||||
<span *ngIf="isFieldEnabled('countryId')">Country :
|
||||
{{getSelectedValue('countryIdOptions',address.countryId)?.name}}<br /></span>
|
||||
<span *ngIf="isFieldEnabled('postalCode')">Postal Code : {{address.postalCode}}<br /></span>
|
||||
<span *ngIf="isFieldEnabled('isActive')">Active Status : {{address.isActive}}<br /></span>
|
||||
</p>
|
||||
|
||||
</mat-expansion-panel>
|
||||
|
||||
</mat-accordion>
|
||||
|
||||
<div fxLayout="row" class="margin-t" fxLayout.xs="column" fxLayoutAlign="center" fxLayoutGap="2%">
|
||||
<button mat-raised-button matStepperPrevious>
|
||||
<fa-icon icon="arrow-left"></fa-icon>
|
||||
Previous
|
||||
</button>
|
||||
<button mat-raised-button matStepperNext>
|
||||
Next
|
||||
<fa-icon icon="arrow-right"></fa-icon>
|
||||
</button>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
@@ -0,0 +1,19 @@
|
||||
.address {
|
||||
.address-actions{
|
||||
margin-top: 1%;
|
||||
button{
|
||||
margin-right: 1%;
|
||||
}
|
||||
}
|
||||
h3 {
|
||||
margin: 1% auto;
|
||||
}
|
||||
p {
|
||||
line-height: 30px;
|
||||
margin-left: 2%;
|
||||
}
|
||||
}
|
||||
|
||||
.margin-t {
|
||||
margin-top: 2em;
|
||||
}
|
||||
+25
@@ -0,0 +1,25 @@
|
||||
import { async, ComponentFixture, TestBed } from '@angular/core/testing';
|
||||
|
||||
import { ClientAddressStepComponent } from './client-address-step.component';
|
||||
|
||||
describe('ClientAddressStepComponent', () => {
|
||||
let component: ClientAddressStepComponent;
|
||||
let fixture: ComponentFixture<ClientAddressStepComponent>;
|
||||
|
||||
beforeEach(async(() => {
|
||||
TestBed.configureTestingModule({
|
||||
declarations: [ ClientAddressStepComponent ]
|
||||
})
|
||||
.compileComponents();
|
||||
}));
|
||||
|
||||
beforeEach(() => {
|
||||
fixture = TestBed.createComponent(ClientAddressStepComponent);
|
||||
component = fixture.componentInstance;
|
||||
fixture.detectChanges();
|
||||
});
|
||||
|
||||
it('should create', () => {
|
||||
expect(component).toBeTruthy();
|
||||
});
|
||||
});
|
||||
@@ -0,0 +1,222 @@
|
||||
/** Angular Imports */
|
||||
import { Component, Input } from '@angular/core';
|
||||
import { MatDialog } from '@angular/material';
|
||||
|
||||
/** Custom Models */
|
||||
import { FormfieldBase } from 'app/shared/form-dialog/formfield/model/formfield-base';
|
||||
import { InputBase } from 'app/shared/form-dialog/formfield/model/input-base';
|
||||
import { SelectBase } from 'app/shared/form-dialog/formfield/model/select-base';
|
||||
|
||||
/** Custom Dialogs */
|
||||
import { FormDialogComponent } from 'app/shared/form-dialog/form-dialog.component';
|
||||
import { DeleteDialogComponent } from 'app/shared/delete-dialog/delete-dialog.component';
|
||||
|
||||
/**
|
||||
* Client Address Step Component
|
||||
*/
|
||||
@Component({
|
||||
selector: 'mifosx-client-address-step',
|
||||
templateUrl: './client-address-step.component.html',
|
||||
styleUrls: ['./client-address-step.component.scss']
|
||||
})
|
||||
export class ClientAddressStepComponent {
|
||||
|
||||
/** Client Address Field Config */
|
||||
@Input() clientAddressFieldConfig: any;
|
||||
/** Client Template */
|
||||
@Input() clientTemplate: any;
|
||||
|
||||
/** Client Address Data */
|
||||
clientAddressData: any[] = [];
|
||||
|
||||
/**
|
||||
* @param {MatDialog} dialog Mat Dialog
|
||||
*/
|
||||
constructor(private dialog: MatDialog) { }
|
||||
|
||||
/**
|
||||
* Adds a client address
|
||||
*/
|
||||
addAddress() {
|
||||
const data = {
|
||||
title: 'Add Client Address',
|
||||
formfields: this.getAddressFormFields()
|
||||
};
|
||||
const addAddressDialogRef = this.dialog.open(FormDialogComponent, { data });
|
||||
addAddressDialogRef.afterClosed().subscribe((response: any) => {
|
||||
if (response.data) {
|
||||
const addressData = response.data.value;
|
||||
addressData.isActive = false;
|
||||
for (const key in addressData) {
|
||||
if (addressData[key] === '' || addressData[key] === undefined) {
|
||||
delete addressData[key];
|
||||
}
|
||||
}
|
||||
this.clientAddressData.push(addressData);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Edit Address
|
||||
* @param {any} address Address
|
||||
* @param {number} index Address index
|
||||
*/
|
||||
editAddress(address: any, index: number) {
|
||||
const data = {
|
||||
title: 'Edit Client Address',
|
||||
formfields: this.getAddressFormFields(address),
|
||||
layout: { addButtonText: 'Edit' }
|
||||
};
|
||||
const editAddressDialogRef = this.dialog.open(FormDialogComponent, { data });
|
||||
editAddressDialogRef.afterClosed().subscribe((response: any) => {
|
||||
if (response.data) {
|
||||
const addressData = response.data.value;
|
||||
addressData.isActive = address.isActive;
|
||||
for (const key in addressData) {
|
||||
if (addressData[key] === '' || addressData[key] === undefined) {
|
||||
delete addressData[key];
|
||||
}
|
||||
}
|
||||
this.clientAddressData[index] = addressData;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* @param {any} address Client Address
|
||||
* @param {number} index Address index
|
||||
*/
|
||||
deleteAddress(address: any, index: number) {
|
||||
const deleteAddressDialogRef = this.dialog.open(DeleteDialogComponent, {
|
||||
data: { deleteContext: `address type : ${address.addressType} ${index}` }
|
||||
});
|
||||
deleteAddressDialogRef.afterClosed().subscribe((response: any) => {
|
||||
if (response.delete) {
|
||||
this.clientAddressData.splice(index, 1);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Toggles address activity
|
||||
* @param {any} address Address
|
||||
*/
|
||||
toggleAddress(address: any) {
|
||||
address.isActive = address.isActive ? false : true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks if field is enabled in address configuration
|
||||
* @param {any} address Address
|
||||
*/
|
||||
isFieldEnabled(fieldName: any) {
|
||||
return (this.clientAddressFieldConfig.find((fieldObj: any) => fieldObj.field === fieldName)).is_enabled;
|
||||
}
|
||||
|
||||
/**
|
||||
* Retrieves field Id from name.
|
||||
* Find pipe doesn't work with accordian.
|
||||
* @param {any} address Address
|
||||
*/
|
||||
getSelectedValue(fieldName: any, fieldId: any) {
|
||||
return (this.clientTemplate.address[fieldName].find((fieldObj: any) => fieldObj.id === fieldId));
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets formfields for form dialog.
|
||||
* @param {any} address Address
|
||||
*/
|
||||
getAddressFormFields(address?: any) {
|
||||
let formfields: FormfieldBase[] = [];
|
||||
formfields.push(this.isFieldEnabled('addressType') ? new SelectBase({
|
||||
controlName: 'addressTypeId',
|
||||
label: 'Address Type',
|
||||
value: address ? address.addressTypeId : '',
|
||||
options: { label: 'name', value: 'id', data: this.clientTemplate.address.addressTypeIdOptions },
|
||||
order: 1,
|
||||
required: true
|
||||
}) : null);
|
||||
formfields.push(this.isFieldEnabled('street') ? new InputBase({
|
||||
controlName: 'street',
|
||||
label: 'Street',
|
||||
value: address ? address.street : '',
|
||||
type: 'text',
|
||||
required: true,
|
||||
order: 2
|
||||
}) : null);
|
||||
formfields.push(this.isFieldEnabled('addressLine1') ? new InputBase({
|
||||
controlName: 'addressLine1',
|
||||
label: 'Address Line 1',
|
||||
value: address ? address.addressLine1 : '',
|
||||
type: 'text',
|
||||
order: 3
|
||||
}) : null);
|
||||
formfields.push(this.isFieldEnabled('addressLine2') ? new InputBase({
|
||||
controlName: 'addressLine2',
|
||||
label: 'Address Line 2',
|
||||
value: address ? address.addressLine2 : '',
|
||||
type: 'text',
|
||||
order: 4
|
||||
}) : null);
|
||||
formfields.push(this.isFieldEnabled('addressLine3') ? new InputBase({
|
||||
controlName: 'addressLine3',
|
||||
label: 'Address Line 3',
|
||||
value: address ? address.addressLine3 : '',
|
||||
type: 'text',
|
||||
order: 5
|
||||
}) : null);
|
||||
formfields.push(this.isFieldEnabled('townVillage') ? new InputBase({
|
||||
controlName: 'townVillage',
|
||||
label: 'Town / Village',
|
||||
value: address ? address.townVillage : '',
|
||||
type: 'text',
|
||||
order: 6
|
||||
}) : null);
|
||||
formfields.push(this.isFieldEnabled('city') ? new InputBase({
|
||||
controlName: 'city',
|
||||
label: 'City',
|
||||
value: address ? address.city : '',
|
||||
type: 'text',
|
||||
order: 7
|
||||
}) : null);
|
||||
formfields.push(this.isFieldEnabled('stateProvinceId') ? new SelectBase({
|
||||
controlName: 'stateProvinceId',
|
||||
label: 'State / Province',
|
||||
value: address ? address.stateProvinceId : '',
|
||||
options: { label: 'name', value: 'id', data: this.clientTemplate.address.stateProvinceIdOptions },
|
||||
order: 8
|
||||
}) : null);
|
||||
formfields.push(this.isFieldEnabled('countyDistrict') ? new InputBase({
|
||||
controlName: 'countryDistrict',
|
||||
label: 'Country District',
|
||||
value: address ? address.countyDistrict : '',
|
||||
type: 'text',
|
||||
order: 11
|
||||
}) : null);
|
||||
formfields.push(this.isFieldEnabled('countryId') ? new SelectBase({
|
||||
controlName: 'countryId',
|
||||
label: 'Country',
|
||||
value: address ? address.countryId : '',
|
||||
options: { label: 'name', value: 'id', data: this.clientTemplate.address.countryIdOptions },
|
||||
order: 10
|
||||
}) : null);
|
||||
formfields.push(this.isFieldEnabled('postalCode') ? new InputBase({
|
||||
controlName: 'postalCode',
|
||||
label: 'Postal Code',
|
||||
value: address ? address.postalCode : '',
|
||||
type: 'text',
|
||||
order: 11
|
||||
}) : null);
|
||||
formfields = formfields.filter(field => field !== null);
|
||||
return formfields;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the array of client addresses
|
||||
*/
|
||||
get address() {
|
||||
return { address: this.clientAddressData };
|
||||
}
|
||||
|
||||
}
|
||||
+104
@@ -0,0 +1,104 @@
|
||||
<h1 mat-dialog-title>{{ data.context }} Family Member</h1>
|
||||
|
||||
<form [formGroup]="familyMemberForm">
|
||||
|
||||
<div fxLayout="row wrap" fxLayout.lt-md="column" fxLayoutAlign="start center" fxLayoutGap="2%">
|
||||
|
||||
<mat-form-field fxFlex="48%">
|
||||
<mat-label>First Name</mat-label>
|
||||
<input formControlName="firstName" required matInput />
|
||||
<mat-error *ngIf="familyMemberForm.controls.firstName.hasError('required')">
|
||||
First Name is <strong>required</strong>
|
||||
</mat-error>
|
||||
</mat-form-field>
|
||||
|
||||
<mat-form-field fxFlex="48%">
|
||||
<mat-label>Middle Name</mat-label>
|
||||
<input formControlName="middleName" matInput />
|
||||
</mat-form-field>
|
||||
|
||||
<mat-form-field fxFlex="48%">
|
||||
<mat-label>Last Name</mat-label>
|
||||
<input formControlName="lastName" required matInput />
|
||||
<mat-error *ngIf="familyMemberForm.controls.lastName.hasError('required')">
|
||||
Last Name is <strong>required</strong>
|
||||
</mat-error>
|
||||
</mat-form-field>
|
||||
|
||||
<mat-form-field fxFlex="48%">
|
||||
<mat-label>Qualification</mat-label>
|
||||
<input formControlName="qualification" matInput />
|
||||
</mat-form-field>
|
||||
|
||||
<mat-form-field fxFlex="48%">
|
||||
<mat-label>Age</mat-label>
|
||||
<input type="number" formControlName="age" matInput />
|
||||
<mat-error *ngIf="familyMemberForm.controls.age.hasError('required')">
|
||||
Age is <strong>required</strong>
|
||||
</mat-error>
|
||||
</mat-form-field>
|
||||
|
||||
<mat-checkbox formControlName="isDependent" labelPosition="before" fxFlex="48%">Is Dependent?</mat-checkbox>
|
||||
|
||||
<mat-form-field fxFlex="48%">
|
||||
<mat-label>Relationship</mat-label>
|
||||
<mat-select formControlName="relationshipId" required>
|
||||
<mat-option *ngFor="let relation of data.options.relationshipIdOptions" [value]="relation.id">
|
||||
{{ relation.name }}
|
||||
</mat-option>
|
||||
</mat-select>
|
||||
<mat-error *ngIf="familyMemberForm.controls.relationshipId.hasError('required')">
|
||||
Relationship is <strong>required</strong>
|
||||
</mat-error>
|
||||
</mat-form-field>
|
||||
|
||||
<mat-form-field fxFlex="48%">
|
||||
<mat-label>Gender</mat-label>
|
||||
<mat-select formControlName="genderId">
|
||||
<mat-option *ngFor="let gender of data.options.genderIdOptions" [value]="gender.id">
|
||||
{{ gender.name }}
|
||||
</mat-option>
|
||||
</mat-select>
|
||||
<mat-error *ngIf="familyMemberForm.controls.genderId.hasError('required')">
|
||||
Gender is <strong>required</strong>
|
||||
</mat-error>
|
||||
</mat-form-field>
|
||||
|
||||
<mat-form-field fxFlex="48%">
|
||||
<mat-label>Profession</mat-label>
|
||||
<mat-select formControlName="professionId">
|
||||
<mat-option *ngFor="let profession of data.options.professionIdOptions" [value]="profession.id">
|
||||
{{ profession.name }}
|
||||
</mat-option>
|
||||
</mat-select>
|
||||
</mat-form-field>
|
||||
|
||||
<mat-form-field fxFlex="48%">
|
||||
<mat-label>Marital Status</mat-label>
|
||||
<mat-select formControlName="maritalStatusId">
|
||||
<mat-option *ngFor="let maritalStatus of data.options.maritalStatusIdOptions"
|
||||
[value]="maritalStatus.id">
|
||||
{{ maritalStatus.name }}
|
||||
</mat-option>
|
||||
</mat-select>
|
||||
</mat-form-field>
|
||||
|
||||
|
||||
<mat-form-field fxFlex="98%">
|
||||
<mat-label>Date Of Birth</mat-label>
|
||||
<input formControlName="dateOfBirth" matInput [min]="minDate" [max]="maxDate" [matDatepicker]="dueDatePicker">
|
||||
<mat-datepicker-toggle matSuffix [for]="dueDatePicker"></mat-datepicker-toggle>
|
||||
<mat-datepicker #dueDatePicker></mat-datepicker>
|
||||
<mat-error *ngIf="familyMemberForm.controls.dateOfBirth.hasError('required')">
|
||||
Date of birth is <strong>required</strong>
|
||||
</mat-error>
|
||||
</mat-form-field>
|
||||
|
||||
</div>
|
||||
|
||||
<mat-dialog-actions align="center">
|
||||
<button mat-raised-button mat-dialog-close>Cancel</button>
|
||||
<button mat-raised-button color="primary" [disabled]="!familyMemberForm.valid" [mat-dialog-close]="{ member: familyMember }">Confirm</button>
|
||||
</mat-dialog-actions>
|
||||
|
||||
</form>
|
||||
+25
@@ -0,0 +1,25 @@
|
||||
import { async, ComponentFixture, TestBed } from '@angular/core/testing';
|
||||
|
||||
import { ClientFamilyMemberDialogComponent } from './client-family-member-dialog.component';
|
||||
|
||||
describe('ClientFamilyMemberDialogComponent', () => {
|
||||
let component: ClientFamilyMemberDialogComponent;
|
||||
let fixture: ComponentFixture<ClientFamilyMemberDialogComponent>;
|
||||
|
||||
beforeEach(async(() => {
|
||||
TestBed.configureTestingModule({
|
||||
declarations: [ ClientFamilyMemberDialogComponent ]
|
||||
})
|
||||
.compileComponents();
|
||||
}));
|
||||
|
||||
beforeEach(() => {
|
||||
fixture = TestBed.createComponent(ClientFamilyMemberDialogComponent);
|
||||
component = fixture.componentInstance;
|
||||
fixture.detectChanges();
|
||||
});
|
||||
|
||||
it('should create', () => {
|
||||
expect(component).toBeTruthy();
|
||||
});
|
||||
});
|
||||
+97
@@ -0,0 +1,97 @@
|
||||
/** Angular Imports */
|
||||
import { Component, OnInit, Inject } from '@angular/core';
|
||||
import { MatDialogRef, MAT_DIALOG_DATA } from '@angular/material';
|
||||
import { FormGroup, FormBuilder, Validators } from '@angular/forms';
|
||||
import { DatePipe } from '@angular/common';
|
||||
|
||||
/**
|
||||
* Client Family Members Dialog
|
||||
*/
|
||||
@Component({
|
||||
selector: 'mifosx-client-family-member-dialog',
|
||||
templateUrl: './client-family-member-dialog.component.html',
|
||||
styleUrls: ['./client-family-member-dialog.component.scss']
|
||||
})
|
||||
export class ClientFamilyMemberDialogComponent implements OnInit {
|
||||
|
||||
/** Minimum Due Date allowed. */
|
||||
minDate = new Date(2000, 0, 1);
|
||||
/** Maximum Due Date allowed. */
|
||||
maxDate = new Date();
|
||||
|
||||
/** Add/Edit family member form. */
|
||||
familyMemberForm: FormGroup;
|
||||
|
||||
/**
|
||||
* @param {MatDialogRef} dialogRef Client Family Member Dialog Reference
|
||||
* @param {FormBuilder} formBuilder Form Builder
|
||||
* @param {DatePipe} datePipe Date Pipe
|
||||
* @param {any} data Dialog Data
|
||||
*/
|
||||
constructor(public dialogRef: MatDialogRef<ClientFamilyMemberDialogComponent>,
|
||||
private formBuilder: FormBuilder,
|
||||
private datePipe: DatePipe,
|
||||
@Inject(MAT_DIALOG_DATA) public data: any) { }
|
||||
|
||||
ngOnInit() {
|
||||
this.createFamilyMemberForm();
|
||||
if (this.data.context === 'Edit') {
|
||||
this.familyMemberForm.patchValue({
|
||||
'firstName': this.data.member.firstName,
|
||||
'middleName': this.data.member.middleName,
|
||||
'lastName': this.data.member.lastName,
|
||||
'qualification': this.data.member.qualification,
|
||||
'age': this.data.member.age,
|
||||
'isDependent': this.data.member.isDependent,
|
||||
'relationshipId': this.data.member.relationshipId,
|
||||
'genderId': this.data.member.genderId,
|
||||
'professionId': this.data.member.professionId,
|
||||
'maritalStatusId': this.data.member.maritalStatusId,
|
||||
'dateOfBirth': this.data.member.dateOfBirth && new Date(this.data.member.dateOfBirth)
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates Family Member Form
|
||||
*/
|
||||
createFamilyMemberForm() {
|
||||
this.familyMemberForm = this.formBuilder.group({
|
||||
'firstName': ['', Validators.required],
|
||||
'middleName': [''],
|
||||
'lastName': ['', Validators.required],
|
||||
'qualification': [''],
|
||||
'age': [''],
|
||||
'isDependent': [''],
|
||||
'relationshipId': ['', Validators.required],
|
||||
'genderId': [''],
|
||||
'professionId': [''],
|
||||
'maritalStatusId': [''],
|
||||
'dateOfBirth': ['']
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns Formatted Family Member
|
||||
*/
|
||||
get familyMember() {
|
||||
const locale = 'en';
|
||||
const dateFormat = 'dd MMMM yyyy';
|
||||
// TODO: Update once language and date settings are setup
|
||||
const familyMember = {
|
||||
...this.familyMemberForm.value,
|
||||
dateFormat,
|
||||
locale
|
||||
};
|
||||
for (const key in familyMember) {
|
||||
if (familyMember[key] === '' || familyMember[key] === undefined) {
|
||||
delete familyMember[key];
|
||||
}
|
||||
}
|
||||
if (familyMember.dateOfBirth) {
|
||||
familyMember.dateOfBirth = this.datePipe.transform(familyMember.dateOfBirth, dateFormat);
|
||||
}
|
||||
return familyMember;
|
||||
}
|
||||
|
||||
}
|
||||
+67
@@ -0,0 +1,67 @@
|
||||
<div class="mat-typography">
|
||||
|
||||
<h3>Family Members</h3>
|
||||
|
||||
<div fxLayout="row" fxLayoutAlign="flex-end" class="m-b-20">
|
||||
<button mat-raised-button color="primary" (click)="addFamilyMember()">
|
||||
<fa-icon icon="plus"></fa-icon> Add
|
||||
</button>
|
||||
</div>
|
||||
|
||||
<mat-accordion>
|
||||
|
||||
<mat-expansion-panel *ngFor="let member of clientFamilyMembers;index as i" class="family-member">
|
||||
|
||||
<mat-expansion-panel-header>
|
||||
|
||||
<mat-panel-title>
|
||||
{{ member.firstName }} {{ member.middleName ? member.middleName + ' ' + member.lastName : member.lastName }}
|
||||
</mat-panel-title>
|
||||
|
||||
<mat-panel-description>
|
||||
{{member.relationship}}
|
||||
</mat-panel-description>
|
||||
|
||||
</mat-expansion-panel-header>
|
||||
|
||||
<mat-divider></mat-divider>
|
||||
|
||||
<div class="family-member-actions" fxLayout="row" fxLayoutAlign="flex-end">
|
||||
<button mat-button color="primary">
|
||||
<fa-icon icon="edit" (click)="editFamilyMember(member, i)"></fa-icon>
|
||||
</button>
|
||||
<button mat-button color="warn" (click)="deleteFamilyMember(member.firstName,i)">
|
||||
<fa-icon icon="trash"></fa-icon>
|
||||
</button>
|
||||
</div>
|
||||
|
||||
<p>
|
||||
First Name : {{ member.firstName }}<br />
|
||||
Middle Name : {{ member.middleName }}<br />
|
||||
Last Name : {{ member.lastName }}<br />
|
||||
Qualification : {{ member.qualification }}<br />
|
||||
Relationship : {{ member.relationshipId | find:clientTemplate.familyMemberOptions.relationshipIdOptions:'id':'name' }}<br />
|
||||
Age : {{ member.age }}<br />
|
||||
Is Dependent : {{ member.isDependent ? 'Yes' : 'No' }}<br />
|
||||
Marital Status : {{ member.maritalStatusId | find:clientTemplate.familyMemberOptions.maritalStatusIdOptions:'id':'name' }}<br />
|
||||
Gender : {{ member.genderId | find:clientTemplate.familyMemberOptions.genderIdOptions:'id':'name' }}<br />
|
||||
Profession : {{member.professionId | find:clientTemplate.familyMemberOptions.professionIdOptions:'id':'name' }}<br />
|
||||
Date Of Birth : {{member.dateOfBirth | date}}<br />
|
||||
</p>
|
||||
|
||||
</mat-expansion-panel>
|
||||
|
||||
</mat-accordion>
|
||||
|
||||
<div fxLayout="row" class="margin-t" fxLayout.xs="column" fxLayoutAlign="center" fxLayoutGap="2%">
|
||||
<button mat-raised-button matStepperPrevious>
|
||||
<fa-icon icon="arrow-left"></fa-icon>
|
||||
Previous
|
||||
</button>
|
||||
<button mat-raised-button matStepperNext>
|
||||
Next
|
||||
<fa-icon icon="arrow-right"></fa-icon>
|
||||
</button>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
+19
@@ -0,0 +1,19 @@
|
||||
.family-member {
|
||||
.family-member-actions{
|
||||
margin-top: 1%;
|
||||
button{
|
||||
margin-right: 1%;
|
||||
}
|
||||
}
|
||||
h3 {
|
||||
margin: 1% auto;
|
||||
}
|
||||
p {
|
||||
line-height: 30px;
|
||||
margin-left: 2%;
|
||||
}
|
||||
}
|
||||
|
||||
.margin-t {
|
||||
margin-top: 2em;
|
||||
}
|
||||
+25
@@ -0,0 +1,25 @@
|
||||
import { async, ComponentFixture, TestBed } from '@angular/core/testing';
|
||||
|
||||
import { ClientFamilyMembersStepComponent } from './client-family-members-step.component';
|
||||
|
||||
describe('ClientFamilyMembersStepComponent', () => {
|
||||
let component: ClientFamilyMembersStepComponent;
|
||||
let fixture: ComponentFixture<ClientFamilyMembersStepComponent>;
|
||||
|
||||
beforeEach(async(() => {
|
||||
TestBed.configureTestingModule({
|
||||
declarations: [ ClientFamilyMembersStepComponent ]
|
||||
})
|
||||
.compileComponents();
|
||||
}));
|
||||
|
||||
beforeEach(() => {
|
||||
fixture = TestBed.createComponent(ClientFamilyMembersStepComponent);
|
||||
component = fixture.componentInstance;
|
||||
fixture.detectChanges();
|
||||
});
|
||||
|
||||
it('should create', () => {
|
||||
expect(component).toBeTruthy();
|
||||
});
|
||||
});
|
||||
+90
@@ -0,0 +1,90 @@
|
||||
/** Angular Imports */
|
||||
import { Component, OnInit, Input } from '@angular/core';
|
||||
import { Router, ActivatedRoute } from '@angular/router';
|
||||
import { MatDialog } from '@angular/material';
|
||||
|
||||
/** Custom Components */
|
||||
import { DeleteDialogComponent } from 'app/shared/delete-dialog/delete-dialog.component';
|
||||
import { ClientFamilyMemberDialogComponent } from './client-family-member-dialog/client-family-member-dialog.component';
|
||||
|
||||
/**
|
||||
* Client Family Members Step
|
||||
*/
|
||||
@Component({
|
||||
selector: 'mifosx-client-family-members-step',
|
||||
templateUrl: './client-family-members-step.component.html',
|
||||
styleUrls: ['./client-family-members-step.component.scss']
|
||||
})
|
||||
export class ClientFamilyMembersStepComponent {
|
||||
|
||||
/** Cient Template */
|
||||
@Input() clientTemplate: any;
|
||||
/** Client Family Members */
|
||||
clientFamilyMembers: any[] = [];
|
||||
|
||||
/**
|
||||
* @param {MatDialog} dialog Mat Dialog
|
||||
*/
|
||||
constructor(public dialog: MatDialog) { }
|
||||
|
||||
/**
|
||||
* Adds a family member.
|
||||
*/
|
||||
addFamilyMember() {
|
||||
const addFamilyMemberDialogRef = this.dialog.open(ClientFamilyMemberDialogComponent, {
|
||||
data: {
|
||||
context: 'Add',
|
||||
options: this.clientTemplate.familyMemberOptions,
|
||||
},
|
||||
width: '50rem'
|
||||
});
|
||||
addFamilyMemberDialogRef.afterClosed().subscribe((response: any) => {
|
||||
if (response.member) {
|
||||
this.clientFamilyMembers.push(response.member);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Edits the family member.
|
||||
* @param {any} member Family Member
|
||||
* @param {any} index Tree Index
|
||||
*/
|
||||
editFamilyMember(member: any, index: any) {
|
||||
const addFamilyMemberDialogRef = this.dialog.open(ClientFamilyMemberDialogComponent, {
|
||||
data: {
|
||||
context: 'Edit',
|
||||
member: member,
|
||||
options: this.clientTemplate.familyMemberOptions,
|
||||
},
|
||||
width: '50rem'
|
||||
});
|
||||
addFamilyMemberDialogRef.afterClosed().subscribe((response: any) => {
|
||||
if (response.member) {
|
||||
this.clientFamilyMembers.splice(index, 1, response.member);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Deletes the family member
|
||||
*/
|
||||
deleteFamilyMember(name: string, index: number) {
|
||||
const deleteFamilyMemberDialogRef = this.dialog.open(DeleteDialogComponent, {
|
||||
data: { deleteContext: `Family member name : ${name} ${index}` }
|
||||
});
|
||||
deleteFamilyMemberDialogRef.afterClosed().subscribe((response: any) => {
|
||||
if (response.delete) {
|
||||
this.clientFamilyMembers.splice(index, 1);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the array of client family members.
|
||||
*/
|
||||
get familyMembers() {
|
||||
return { familyMembers: this.clientFamilyMembers };
|
||||
}
|
||||
|
||||
}
|
||||
+215
@@ -0,0 +1,215 @@
|
||||
<form [formGroup]="createClientForm">
|
||||
|
||||
<div fxLayout="row wrap" fxLayoutGap="2%" fxLayout.lt-md="column">
|
||||
|
||||
<mat-form-field fxFlex="48%">
|
||||
<mat-label>Office</mat-label>
|
||||
<mat-select required formControlName="officeId">
|
||||
<mat-option *ngFor="let office of officeOptions" [value]="office.id">
|
||||
{{ office.name }}
|
||||
</mat-option>
|
||||
</mat-select>
|
||||
<mat-error *ngIf="createClientForm.controls.officeId.hasError('required')">
|
||||
Office is <strong>required</strong>
|
||||
</mat-error>
|
||||
</mat-form-field>
|
||||
|
||||
<mat-form-field fxFlex="48%">
|
||||
<mat-label>Staff</mat-label>
|
||||
<mat-select formControlName="staffId">
|
||||
<mat-option *ngFor="let staff of staffOptions" [value]="staff.id">
|
||||
{{ staff.displayName }}
|
||||
</mat-option>
|
||||
</mat-select>
|
||||
</mat-form-field>
|
||||
|
||||
<mat-form-field fxFlex="48%">
|
||||
<mat-label>Legal Form</mat-label>
|
||||
<mat-select formControlName="legalFormId">
|
||||
<mat-option *ngFor="let legalForm of legalFormOptions" [value]="legalForm.id">
|
||||
{{ legalForm.value }}
|
||||
</mat-option>
|
||||
</mat-select>
|
||||
</mat-form-field>
|
||||
|
||||
<mat-form-field *ngIf="createClientForm.contains('fullname')" fxFlex="48%">
|
||||
<mat-label>Name</mat-label>
|
||||
<input matInput required formControlName="fullname">
|
||||
<mat-error *ngIf="createClientForm.controls.fullname.hasError('required')">
|
||||
Client name is <strong>required</strong>
|
||||
</mat-error>
|
||||
<mat-error *ngIf="createClientForm.controls.fullname.hasError('pattern')">
|
||||
Client name <strong>cannot</strong> begin with a special character or number
|
||||
</mat-error>
|
||||
</mat-form-field>
|
||||
|
||||
<mat-form-field *ngIf="createClientForm.contains('firstname')" fxFlex="48%">
|
||||
<mat-label>First Name</mat-label>
|
||||
<input matInput required formControlName="firstname">
|
||||
<mat-error *ngIf="createClientForm.controls.firstname.hasError('required')">
|
||||
Client first name is <strong>required</strong>
|
||||
</mat-error>
|
||||
<mat-error *ngIf="createClientForm.controls.firstname.hasError('pattern')">
|
||||
Client first name <strong>cannot</strong> begin with a special character or number
|
||||
</mat-error>
|
||||
</mat-form-field>
|
||||
|
||||
<mat-form-field *ngIf="createClientForm.contains('middlename')" fxFlex="48%">
|
||||
<mat-label>Middle Name</mat-label>
|
||||
<input matInput formControlName="middlename">
|
||||
<mat-error *ngIf="createClientForm.controls.middlename.hasError('pattern')">
|
||||
Client middle name <strong>cannot</strong> begin with a special character or number
|
||||
</mat-error>
|
||||
</mat-form-field>
|
||||
|
||||
<mat-form-field *ngIf="createClientForm.contains('lastname')" fxFlex="48%">
|
||||
<mat-label>Last Name</mat-label>
|
||||
<input matInput required formControlName="lastname">
|
||||
<mat-error *ngIf="createClientForm.controls.lastname.hasError('required')">
|
||||
Client last name is <strong>required</strong>
|
||||
</mat-error>
|
||||
<mat-error *ngIf="createClientForm.controls.lastname.hasError('pattern')">
|
||||
Client last name <strong>cannot</strong> begin with a special character or number
|
||||
</mat-error>
|
||||
</mat-form-field>
|
||||
|
||||
<mat-form-field fxFlex="48%">
|
||||
<mat-label>{{ createClientForm.value.legalFormId === 1 ? 'Date of Birth' : 'Incorporation Date' }}</mat-label>
|
||||
<input matInput [max]="maxDate" [matDatepicker]="dateOfBirthDatePicker" formControlName="dateOfBirth">
|
||||
<mat-datepicker-toggle matSuffix [for]="dateOfBirthDatePicker"></mat-datepicker-toggle>
|
||||
<mat-datepicker #dateOfBirthDatePicker></mat-datepicker>
|
||||
</mat-form-field>
|
||||
|
||||
<mat-form-field fxFlex="48%">
|
||||
<mat-label>External Id</mat-label>
|
||||
<input matInput formControlName="externalId">
|
||||
</mat-form-field>
|
||||
|
||||
<mat-form-field fxFlex="48%">
|
||||
<mat-label>Mobile No</mat-label>
|
||||
<input matInput type="number" formControlName="mobileNo">
|
||||
</mat-form-field>
|
||||
|
||||
<mat-form-field *ngIf="createClientForm.value.legalFormId === 1" fxFlex="48%">
|
||||
<mat-label>Gender</mat-label>
|
||||
<mat-select formControlName="genderId">
|
||||
<mat-option *ngFor="let gender of genderOptions" [value]="gender.id">
|
||||
{{ gender.name }}
|
||||
</mat-option>
|
||||
</mat-select>
|
||||
</mat-form-field>
|
||||
|
||||
<mat-checkbox *ngIf="createClientForm.value.legalFormId === 1" fxFlex="48%" labelPosition="before" formControlName="isStaff" class="margin-v">
|
||||
Is staff?
|
||||
</mat-checkbox>
|
||||
|
||||
<mat-form-field fxFlex="48%">
|
||||
<mat-label>Client Type</mat-label>
|
||||
<mat-select formControlName="clientTypeId">
|
||||
<mat-option *ngFor="let clientType of clientTypeOptions" [value]="clientType.id">
|
||||
{{ clientType.name }}
|
||||
</mat-option>
|
||||
</mat-select>
|
||||
</mat-form-field>
|
||||
|
||||
<mat-form-field fxFlex="48%">
|
||||
<mat-label>Client Classification</mat-label>
|
||||
<mat-select formControlName="clientClassificationId">
|
||||
<mat-option *ngFor="let clientClassification of clientClassificationTypeOptions" [value]="clientClassification.id">
|
||||
{{ clientClassification.name }}
|
||||
</mat-option>
|
||||
</mat-select>
|
||||
</mat-form-field>
|
||||
|
||||
<mat-form-field fxFlex="48%">
|
||||
<mat-label>Submitted On</mat-label>
|
||||
<input matInput [min]="minDate" [max]="maxDate" [matDatepicker]="submittedOnDatePicker" formControlName="submittedOnDate">
|
||||
<mat-datepicker-toggle matSuffix [for]="submittedOnDatePicker"></mat-datepicker-toggle>
|
||||
<mat-datepicker #submittedOnDatePicker></mat-datepicker>
|
||||
</mat-form-field>
|
||||
|
||||
<mat-checkbox fxFlex="48%" labelPosition="before" formControlName="active" class="margin-v">
|
||||
Active?
|
||||
</mat-checkbox>
|
||||
|
||||
<mat-form-field *ngIf="createClientForm.contains('activationDate')" fxFlex="48%">
|
||||
<mat-label>Activation Date</mat-label>
|
||||
<input matInput [min]="minDate" [max]="maxDate" [matDatepicker]="activatedOnDatePicker" required
|
||||
formControlName="activationDate">
|
||||
<mat-datepicker-toggle matSuffix [for]="activatedOnDatePicker"></mat-datepicker-toggle>
|
||||
<mat-datepicker #activatedOnDatePicker></mat-datepicker>
|
||||
<mat-error *ngIf="createClientForm.controls.activationDate.hasError('required')">
|
||||
Activation Date is <strong>required</strong>
|
||||
</mat-error>
|
||||
</mat-form-field>
|
||||
|
||||
<mat-checkbox fxFlex="48%" labelPosition="before" formControlName="addSavings" class="margin-v">
|
||||
Open Savings Account?
|
||||
</mat-checkbox>
|
||||
|
||||
<mat-form-field *ngIf="createClientForm.contains('savingsProductId')" fxFlex="48%">
|
||||
<mat-label>Savings Product</mat-label>
|
||||
<mat-select required formControlName="savingsProductId">
|
||||
<mat-option *ngFor="let product of savingProductOptions" [value]="product.id">
|
||||
{{ product.name }}
|
||||
</mat-option>
|
||||
</mat-select>
|
||||
<mat-error *ngIf="createClientForm.controls.savingsProductId.hasError('required')">
|
||||
Savings product is <strong>required</strong>
|
||||
</mat-error>
|
||||
</mat-form-field>
|
||||
|
||||
<div fxFlex="100%" fxLayout="row wrap" fxLayoutGap="2%" fxLayout.lt-md="column" formGroupName="clientNonPersonDetails"
|
||||
*ngIf="createClientForm.contains('clientNonPersonDetails')">
|
||||
|
||||
<mat-form-field fxFlex="48%">
|
||||
<mat-label>Incorporation Validity Till Date</mat-label>
|
||||
<input matInput [min]="minDate" [max]="maxDate" [matDatepicker]="incorpValidityTillDateDatePicker" formControlName="incorpValidityTillDate">
|
||||
<mat-datepicker-toggle matSuffix [for]="incorpValidityTillDateDatePicker"></mat-datepicker-toggle>
|
||||
<mat-datepicker #incorpValidityTillDateDatePicker></mat-datepicker>
|
||||
</mat-form-field>
|
||||
|
||||
<mat-form-field fxFlex="48%">
|
||||
<mat-label>Incorporation Number</mat-label>
|
||||
<input matInput formControlName="incorpNumber">
|
||||
</mat-form-field>
|
||||
|
||||
<mat-form-field fxFlex="48%">
|
||||
<mat-label>Main Business Line</mat-label>
|
||||
<mat-select formControlName="mainBusinessLineId">
|
||||
<mat-option *ngFor="let business of businessLineOptions" [value]="business.id">
|
||||
{{ business.name }}
|
||||
</mat-option>
|
||||
</mat-select>
|
||||
</mat-form-field>
|
||||
|
||||
<mat-form-field fxFlex="48%">
|
||||
<mat-label>Constitution</mat-label>
|
||||
<mat-select formControlName="constitutionId">
|
||||
<mat-option *ngFor="let constitution of constitutionOptions" [value]="constitution.id">
|
||||
{{ constitution.name }}
|
||||
</mat-option>
|
||||
</mat-select>
|
||||
</mat-form-field>
|
||||
|
||||
<mat-form-field fxFlex="98%">
|
||||
<mat-label>Remarks</mat-label>
|
||||
<textarea matInput formControlName="remarks"></textarea>
|
||||
</mat-form-field>
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
<div fxLayout="row" class="margin-t" fxLayout.xs="column" fxLayoutAlign="center" fxLayoutGap="2%">
|
||||
<button mat-raised-button matStepperPrevious disabled>
|
||||
<fa-icon icon="arrow-left"></fa-icon>
|
||||
Previous
|
||||
</button>
|
||||
<button mat-raised-button matStepperNext>
|
||||
Next
|
||||
<fa-icon icon="arrow-right"></fa-icon>
|
||||
</button>
|
||||
</div>
|
||||
|
||||
</form>
|
||||
@@ -0,0 +1,7 @@
|
||||
.margin-v {
|
||||
margin: 2em 0 0 0;
|
||||
}
|
||||
|
||||
.margin-t {
|
||||
margin-top: 2em;
|
||||
}
|
||||
+25
@@ -0,0 +1,25 @@
|
||||
import { async, ComponentFixture, TestBed } from '@angular/core/testing';
|
||||
|
||||
import { ClientGeneralStepComponent } from './client-general-step.component';
|
||||
|
||||
describe('ClientGeneralStepComponent', () => {
|
||||
let component: ClientGeneralStepComponent;
|
||||
let fixture: ComponentFixture<ClientGeneralStepComponent>;
|
||||
|
||||
beforeEach(async(() => {
|
||||
TestBed.configureTestingModule({
|
||||
declarations: [ ClientGeneralStepComponent ]
|
||||
})
|
||||
.compileComponents();
|
||||
}));
|
||||
|
||||
beforeEach(() => {
|
||||
fixture = TestBed.createComponent(ClientGeneralStepComponent);
|
||||
component = fixture.componentInstance;
|
||||
fixture.detectChanges();
|
||||
});
|
||||
|
||||
it('should create', () => {
|
||||
expect(component).toBeTruthy();
|
||||
});
|
||||
});
|
||||
@@ -0,0 +1,172 @@
|
||||
/** Angular Imports */
|
||||
import { Component, OnInit, Input } from '@angular/core';
|
||||
import { FormBuilder, FormGroup, Validators, FormControl } from '@angular/forms';
|
||||
import { DatePipe } from '@angular/common';
|
||||
|
||||
/**
|
||||
* Create Client Component
|
||||
*/
|
||||
@Component({
|
||||
selector: 'mifosx-client-general-step',
|
||||
templateUrl: './client-general-step.component.html',
|
||||
styleUrls: ['./client-general-step.component.scss']
|
||||
})
|
||||
export class ClientGeneralStepComponent implements OnInit {
|
||||
|
||||
/** Minimum date allowed. */
|
||||
minDate = new Date(2000, 0, 1);
|
||||
/** Maximum date allowed. */
|
||||
maxDate = new Date();
|
||||
|
||||
/** Client Template */
|
||||
@Input() clientTemplate: any;
|
||||
/** Create Client Form */
|
||||
createClientForm: FormGroup;
|
||||
|
||||
/** Office Options */
|
||||
officeOptions: any;
|
||||
/** Staff Options */
|
||||
staffOptions: any;
|
||||
/** Legal Form Options */
|
||||
legalFormOptions: any;
|
||||
/** Client Type Options */
|
||||
clientTypeOptions: any;
|
||||
/** Client Classification Options */
|
||||
clientClassificationTypeOptions: any;
|
||||
/** Business Line Options */
|
||||
businessLineOptions: any;
|
||||
/** Constitution Options */
|
||||
constitutionOptions: any;
|
||||
/** Gender Options */
|
||||
genderOptions: any;
|
||||
/** Saving Product Options */
|
||||
savingProductOptions: any;
|
||||
|
||||
/**
|
||||
* @param {FormBuilder} formBuilder Form Builder
|
||||
* @param {DatePipe} datePipe Date Pipe
|
||||
*/
|
||||
constructor(private formBuilder: FormBuilder,
|
||||
private datePipe: DatePipe) {
|
||||
this.setClientForm();
|
||||
}
|
||||
|
||||
ngOnInit() {
|
||||
this.setOptions();
|
||||
this.buildDependencies();
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates the client form.
|
||||
*/
|
||||
setClientForm() {
|
||||
this.createClientForm = this.formBuilder.group({
|
||||
'officeId': ['', Validators.required],
|
||||
'staffId': [''],
|
||||
'legalFormId': [''],
|
||||
'isStaff': [false],
|
||||
'active': [false],
|
||||
'addSavings': [false],
|
||||
'accountNo': [''],
|
||||
'externalId': [''],
|
||||
'genderId': [''],
|
||||
'mobileNo': [''],
|
||||
'dateOfBirth': [''],
|
||||
'clientTypeId': [''],
|
||||
'clientClassificationId': [''],
|
||||
'submittedOnDate': ['']
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets select dropdown options.
|
||||
*/
|
||||
setOptions() {
|
||||
this.officeOptions = this.clientTemplate.officeOptions;
|
||||
this.staffOptions = this.clientTemplate.staffOptions;
|
||||
this.legalFormOptions = this.clientTemplate.clientLegalFormOptions;
|
||||
this.clientTypeOptions = this.clientTemplate.clientTypeOptions;
|
||||
this.clientClassificationTypeOptions = this.clientTemplate.clientClassificationOptions;
|
||||
this.businessLineOptions = this.clientTemplate.clientNonPersonMainBusinessLineOptions;
|
||||
this.constitutionOptions = this.clientTemplate.clientNonPersonConstitutionOptions;
|
||||
this.genderOptions = this.clientTemplate.genderOptions;
|
||||
this.savingProductOptions = this.clientTemplate.savingProductOptions;
|
||||
}
|
||||
|
||||
/**
|
||||
* Adds controls conditionally.
|
||||
*/
|
||||
buildDependencies() {
|
||||
this.createClientForm.get('legalFormId').valueChanges.subscribe((legalFormId: any) => {
|
||||
if (legalFormId === 1) {
|
||||
this.createClientForm.removeControl('fullname');
|
||||
this.createClientForm.removeControl('clientNonPersonDetails');
|
||||
this.createClientForm.addControl('firstname', new FormControl('', [Validators.required, Validators.pattern('(^[A-z]).*')]));
|
||||
this.createClientForm.addControl('middlename', new FormControl('', Validators.pattern('(^[A-z]).*')));
|
||||
this.createClientForm.addControl('lastname', new FormControl('', [Validators.required, Validators.pattern('(^[A-z]).*')]));
|
||||
} else {
|
||||
this.createClientForm.removeControl('firstname');
|
||||
this.createClientForm.removeControl('middlename');
|
||||
this.createClientForm.removeControl('lastname');
|
||||
this.createClientForm.addControl('fullname', new FormControl('', [Validators.required, Validators.pattern('(^[A-z]).*')]));
|
||||
this.createClientForm.addControl('clientNonPersonDetails', this.formBuilder.group({
|
||||
'constitutionId': [''],
|
||||
'incorpValidityTillDate': [''],
|
||||
'incorpNumber': [''],
|
||||
'mainBusinessLineId': [''],
|
||||
'remarks': ['']
|
||||
}));
|
||||
}
|
||||
});
|
||||
this.createClientForm.get('legalFormId').patchValue(1);
|
||||
this.createClientForm.get('active').valueChanges.subscribe((active: boolean) => {
|
||||
if (active) {
|
||||
this.createClientForm.addControl('activationDate', new FormControl('', Validators.required));
|
||||
} else {
|
||||
this.createClientForm.removeControl('activationDate');
|
||||
}
|
||||
});
|
||||
this.createClientForm.get('addSavings').valueChanges.subscribe((active: boolean) => {
|
||||
if (active) {
|
||||
this.createClientForm.addControl('savingsProductId', new FormControl('', Validators.required));
|
||||
} else {
|
||||
this.createClientForm.removeControl('savingsProductId');
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Client General Details
|
||||
*/
|
||||
get clientGeneralDetails() {
|
||||
const generalDetails = this.createClientForm.value;
|
||||
const dateFormat = 'dd MMMM yyyy';
|
||||
const locale = 'en';
|
||||
// TODO: Update once language and date settings are setup
|
||||
for (const key in generalDetails) {
|
||||
if (generalDetails[key] === '' || key === 'addSavings') {
|
||||
delete generalDetails[key];
|
||||
}
|
||||
}
|
||||
if (generalDetails.submittedOnDate) {
|
||||
generalDetails.submittedOnDate = this.datePipe.transform(generalDetails.submittedOnDate, dateFormat);
|
||||
}
|
||||
if (generalDetails.activationDate) {
|
||||
generalDetails.activationDate = this.datePipe.transform(generalDetails.activationDate, dateFormat);
|
||||
}
|
||||
if (generalDetails.dateOfBirth) {
|
||||
generalDetails.dateOfBirth = this.datePipe.transform(generalDetails.dateOfBirth, dateFormat);
|
||||
}
|
||||
|
||||
if (generalDetails.clientNonPersonDetails && generalDetails.clientNonPersonDetails.incorpValidityTillDate) {
|
||||
generalDetails.clientNonPersonDetails = {
|
||||
...generalDetails.clientNonPersonDetails,
|
||||
incorpValidityTillDate: this.datePipe.transform(generalDetails.dateOfBirth, dateFormat),
|
||||
dateFormat,
|
||||
locale
|
||||
};
|
||||
}
|
||||
return generalDetails;
|
||||
}
|
||||
|
||||
}
|
||||
+218
@@ -0,0 +1,218 @@
|
||||
<div fxLayout="row wrap" fxLayout.lt-md="column">
|
||||
|
||||
<h3 class="mat-h3" fxFlexFill>General</h3>
|
||||
|
||||
<mat-divider fxFlexFill></mat-divider>
|
||||
|
||||
<div fxFlexFill>
|
||||
<span fxFlex="40%">Name</span>
|
||||
<span fxFlex="60%" *ngIf="client.legalFormId === 2">{{ client.fullname }}</span>
|
||||
<span fxFlex="60%" *ngIf="client.legalFormId === 1">{{ client.firstname }} {{ client.middlename ? client.middlename + ' ' + client.lastname : client.lastname }}</span>
|
||||
</div>
|
||||
|
||||
<div fxFlexFill>
|
||||
<span fxFlex="40%">Office</span>
|
||||
<span fxFlex="60%">{{ client.officeId | find:clientTemplate.officeOptions:'id':'name' }}</span>
|
||||
</div>
|
||||
|
||||
<div fxFlexFill>
|
||||
<span fxFlex="40%">Legal Form</span>
|
||||
<span fxFlex="60%">{{ client.legalFormId | find:clientTemplate.clientLegalFormOptions:'id':'value' }}</span>
|
||||
</div>
|
||||
|
||||
<div fxFlexFill *ngIf="client.staffId">
|
||||
<span fxFlex="40%">Staff</span>
|
||||
<span fxFlex="60%">{{ client.staffId | find:clientTemplate.staffOptions:'id':'displayName' }}</span>
|
||||
</div>
|
||||
|
||||
<div fxFlexFill *ngIf="client.dateOfBirth">
|
||||
<span fxFlex="40%">{{ client.legalFormId === 1 ? 'Date of Birth' : 'Incorporation Date' }}</span>
|
||||
<span fxFlex="60%">{{ client.dateOfBirth | date }}</span>
|
||||
</div>
|
||||
|
||||
<div fxFlexFill *ngIf="client.externalId">
|
||||
<span fxFlex="40%">External Id</span>
|
||||
<span fxFlex="60%">{{ client.externalId }}</span>
|
||||
</div>
|
||||
|
||||
<div fxFlexFill *ngIf="client.mobileNo">
|
||||
<span fxFlex="40%">Mobile No</span>
|
||||
<span fxFlex="60%">{{ client.mobileNo }}</span>
|
||||
</div>
|
||||
|
||||
<div fxFlexFill *ngIf="client.clientTypeId">
|
||||
<span fxFlex="40%">Client Type</span>
|
||||
<span fxFlex="60%">{{ client.clientTypeId | find:clientTemplate.clientTypeOptions:'id':'name' }}</span>
|
||||
</div>
|
||||
|
||||
<div fxFlexFill *ngIf="client.clientClassificationId">
|
||||
<span fxFlex="40%">Client Classification</span>
|
||||
<span fxFlex="60%">{{ client.clientClassificationId | find:clientTemplate.clientClassificationOptions:'id':'name' }}</span>
|
||||
</div>
|
||||
|
||||
<div fxFlexFill *ngIf="client.savingsProductId">
|
||||
<span fxFlex="40%">Savings Product</span>
|
||||
<span fxFlex="60%">{{ client.savingsProductId | find:clientTemplate.savingProductOptions:'id':'name' }}</span>
|
||||
</div>
|
||||
|
||||
<div fxFlexFill *ngIf="client.submittedOnDate">
|
||||
<span fxFlex="40%">Submitted On Date</span>
|
||||
<span fxFlex="60%">{{ client.submittedOnDate | date }}</span>
|
||||
</div>
|
||||
|
||||
<div fxFlexFill>
|
||||
<span fxFlex="40%">Active?</span>
|
||||
<span fxFlex="60%">{{ client.active ? 'Yes' : 'No' }}</span>
|
||||
</div>
|
||||
|
||||
<div fxFlexFill *ngIf="client.activationDate">
|
||||
<span fxFlex="40%">Activation Date</span>
|
||||
<span fxFlex="60%">{{ client.activationDate | date }}</span>
|
||||
</div>
|
||||
|
||||
<ng-container *ngIf="client.legalFormId === 1">
|
||||
|
||||
<div fxFlexFill *ngIf="client.genderId">
|
||||
<span fxFlex="40%">Gender</span>
|
||||
<span fxFlex="60%">{{ client.genderId | find:clientTemplate.genderOptions:'id':'name' }}</span>
|
||||
</div>
|
||||
|
||||
<div fxFlexFill>
|
||||
<span fxFlex="40%">Is Staff?</span>
|
||||
<span fxFlex="60%">{{ client.isStaff ? 'Yes' : 'No' }}</span>
|
||||
</div>
|
||||
|
||||
</ng-container>
|
||||
|
||||
<ng-container *ngIf="client.legalFormId === 2">
|
||||
|
||||
<div fxFlexFill *ngIf="client.clientNonPersonDetails.incorpValidityTillDate">
|
||||
<span fxFlex="40%">Incorporation Validity Till Date</span>
|
||||
<span fxFlex="60%">{{ client.clientNonPersonDetails.incorpValidityTillDate | date }}</span>
|
||||
</div>
|
||||
|
||||
<div fxFlexFill>
|
||||
<span fxFlex="40%">Incorportation Number</span>
|
||||
<span fxFlex="60%">{{ client.clientNonPersonDetails.incorpNumber || 'Not Provided' }}</span>
|
||||
</div>
|
||||
|
||||
<div fxFlexFill *ngIf="client.clientNonPersonDetails.mainBusinessLineId">
|
||||
<span fxFlex="40%">Main Business Line</span>
|
||||
<span fxFlex="60%">{{ client.clientNonPersonDetails.mainBusinessLineId | find:clientTemplate.clientNonPersonMainBusinessLineOptions:'id':'name' }}</span>
|
||||
</div>
|
||||
|
||||
<div fxFlexFill *ngIf="client.clientNonPersonDetails.constitutionId">
|
||||
<span fxFlex="40%">Constitution</span>
|
||||
<span fxFlex="60%">{{ client.clientNonPersonDetails.constitutionId | find:clientTemplate.clientNonPersonConstitutionOptions:'id':'name'}}</span>
|
||||
</div>
|
||||
|
||||
<div fxFlexFill>
|
||||
<span fxFlex="40%">Remarks</span>
|
||||
<span fxFlex="60%">{{ client.clientNonPersonDetails.remarks || 'N/A' }}</span>
|
||||
</div>
|
||||
|
||||
</ng-container>
|
||||
|
||||
<div fxFlexFill *ngIf="client.familyMembers.length" fxLayout="row wrap" fxLayout.lt-md="column" class="m-b-20">
|
||||
|
||||
<h3 class="mat-h3" fxFlexFill>Family Members</h3>
|
||||
|
||||
<mat-divider fxFlexFill></mat-divider>
|
||||
|
||||
<mat-accordion fxFlexFill class="m-t-5">
|
||||
|
||||
<mat-expansion-panel *ngFor="let member of client.familyMembers" class="family-member">
|
||||
|
||||
<mat-expansion-panel-header>
|
||||
|
||||
<mat-panel-title>
|
||||
{{ member.firstName }} {{ member.middleName ? member.middleName + ' ' + member.lastName : member.lastName }}
|
||||
</mat-panel-title>
|
||||
|
||||
<mat-panel-description>
|
||||
{{member.relationship}}
|
||||
</mat-panel-description>
|
||||
|
||||
</mat-expansion-panel-header>
|
||||
|
||||
<mat-divider></mat-divider>
|
||||
|
||||
<p>
|
||||
First Name : {{ member.firstName }}<br />
|
||||
Middle Name : {{ member.middleName }}<br />
|
||||
Last Name : {{ member.lastName }}<br />
|
||||
Qualification : {{ member.qualification }}<br />
|
||||
Relationship : {{ member.relationshipId | find:clientTemplate.familyMemberOptions.relationshipIdOptions:'id':'name' }}<br />
|
||||
Age : {{ member.age }}<br />
|
||||
Is Dependent : {{ member.isDependent ? 'Yes' : 'No' }}<br />
|
||||
Marital Status : {{ member.maritalStatusId | find:clientTemplate.familyMemberOptions.maritalStatusIdOptions:'id':'name' }}<br />
|
||||
Gender : {{ member.genderId | find:clientTemplate.familyMemberOptions.genderIdOptions:'id':'name' }}<br />
|
||||
Profession : {{ member.professionId | find:clientTemplate.familyMemberOptions.professionIdOptions:'id':'name' }}<br />
|
||||
Date Of Birth : {{ member.dateOfBirth | date }}<br />
|
||||
</p>
|
||||
|
||||
</mat-expansion-panel>
|
||||
|
||||
</mat-accordion>
|
||||
|
||||
</div>
|
||||
|
||||
<div fxFlexFill *ngIf="client.address.length" fxLayout="row wrap" fxLayout.lt-md="column">
|
||||
|
||||
<h3 class="mat-h3" fxFlexFill>Address</h3>
|
||||
|
||||
<mat-divider fxFlexFill></mat-divider>
|
||||
|
||||
<mat-accordion fxFlexFill class="m-t-5">
|
||||
|
||||
<mat-expansion-panel *ngFor="let address of client.address" class="address">
|
||||
|
||||
<mat-expansion-panel-header>
|
||||
|
||||
<mat-panel-title>
|
||||
{{ getSelectedValue('addressTypeIdOptions',address.addressTypeId)?.name }}
|
||||
</mat-panel-title>
|
||||
|
||||
<mat-panel-description>
|
||||
{{address.relationship}}
|
||||
</mat-panel-description>
|
||||
|
||||
</mat-expansion-panel-header>
|
||||
|
||||
<mat-divider></mat-divider>
|
||||
|
||||
<p>
|
||||
<span *ngIf="isFieldEnabled('street')">Street : {{address.street}}<br /></span>
|
||||
<span *ngIf="isFieldEnabled('addressLine1')">Address Line 1 : {{address.addressLine1}}<br /></span>
|
||||
<span *ngIf="isFieldEnabled('addressLine2')">Address Line 2 : {{address.addressLine2}}<br /></span>
|
||||
<span *ngIf="isFieldEnabled('addressLine3')">Address Line 3 : {{address.addressLine3}}<br /></span>
|
||||
<span *ngIf="isFieldEnabled('townVillage')">Town / Village : {{address.townVillage}}<br /></span>
|
||||
<span *ngIf="isFieldEnabled('city')">City : {{address.city}}<br /></span>
|
||||
<span *ngIf="isFieldEnabled('stateProvinceId')">State / Province :
|
||||
{{getSelectedValue('stateProvinceIdOptions',address.stateProvinceId)?.name}}<br /></span>
|
||||
<span *ngIf="isFieldEnabled('countryId')">Country :
|
||||
{{getSelectedValue('countryIdOptions',address.countryId)?.name}}<br /></span>
|
||||
<span *ngIf="isFieldEnabled('postalCode')">Postal Code : {{address.postalCode}}<br /></span>
|
||||
<span *ngIf="isFieldEnabled('isActive')">Active Status : {{address.isActive}}<br /></span>
|
||||
</p>
|
||||
|
||||
</mat-expansion-panel>
|
||||
|
||||
</mat-accordion>
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
<div fxLayout="row" class="margin-t" fxLayout.xs="column" fxLayoutAlign="center" fxLayoutGap="2%">
|
||||
<button mat-raised-button matStepperPrevious>
|
||||
<fa-icon icon="arrow-left"></fa-icon>
|
||||
Previous
|
||||
</button>
|
||||
<button mat-raised-button [routerLink]="['../']">
|
||||
Cancel
|
||||
</button>
|
||||
<button mat-raised-button color="primary" (click)="submit.emit()">
|
||||
Submit
|
||||
</button>
|
||||
</div>
|
||||
@@ -0,0 +1,36 @@
|
||||
h2, h3, h4 {
|
||||
margin: 0;
|
||||
font-weight: 500;
|
||||
}
|
||||
|
||||
span {
|
||||
margin: 0.5em 0;
|
||||
}
|
||||
|
||||
mat-divider {
|
||||
margin: 0 0 0.5em 0;
|
||||
}
|
||||
|
||||
.margin-t {
|
||||
margin-top: 2em;
|
||||
}
|
||||
|
||||
.family-member {
|
||||
h3 {
|
||||
margin: 1% auto;
|
||||
}
|
||||
p {
|
||||
line-height: 30px;
|
||||
margin-left: 2%;
|
||||
}
|
||||
}
|
||||
|
||||
.address {
|
||||
h3 {
|
||||
margin: 1% auto;
|
||||
}
|
||||
p {
|
||||
line-height: 30px;
|
||||
margin-left: 2%;
|
||||
}
|
||||
}
|
||||
+25
@@ -0,0 +1,25 @@
|
||||
import { async, ComponentFixture, TestBed } from '@angular/core/testing';
|
||||
|
||||
import { ClientPreviewStepComponent } from './client-preview-step.component';
|
||||
|
||||
describe('ClientPreviewStepComponent', () => {
|
||||
let component: ClientPreviewStepComponent;
|
||||
let fixture: ComponentFixture<ClientPreviewStepComponent>;
|
||||
|
||||
beforeEach(async(() => {
|
||||
TestBed.configureTestingModule({
|
||||
declarations: [ ClientPreviewStepComponent ]
|
||||
})
|
||||
.compileComponents();
|
||||
}));
|
||||
|
||||
beforeEach(() => {
|
||||
fixture = TestBed.createComponent(ClientPreviewStepComponent);
|
||||
component = fixture.componentInstance;
|
||||
fixture.detectChanges();
|
||||
});
|
||||
|
||||
it('should create', () => {
|
||||
expect(component).toBeTruthy();
|
||||
});
|
||||
});
|
||||
@@ -0,0 +1,44 @@
|
||||
/** Angular Imports */
|
||||
import { Component, Output, EventEmitter, Input } from '@angular/core';
|
||||
|
||||
/**
|
||||
* Client Preview Step Component
|
||||
*/
|
||||
@Component({
|
||||
selector: 'mifosx-client-preview-step',
|
||||
templateUrl: './client-preview-step.component.html',
|
||||
styleUrls: ['./client-preview-step.component.scss']
|
||||
})
|
||||
export class ClientPreviewStepComponent {
|
||||
|
||||
/** Client Address field configuration */
|
||||
@Input() clientAddressFieldConfig: any;
|
||||
/** Client Template */
|
||||
@Input() clientTemplate: any;
|
||||
/** Client Object */
|
||||
@Input() client: any;
|
||||
|
||||
/** Form submission event */
|
||||
@Output() submit = new EventEmitter();
|
||||
|
||||
constructor() { }
|
||||
|
||||
/**
|
||||
* Utilized in address preview.
|
||||
* Find pipe doesn't work with accordian.
|
||||
* @param {any} fieldName Field Name
|
||||
* @param {any} fieldId Field Id
|
||||
*/
|
||||
getSelectedValue(fieldName: any, fieldId: any) {
|
||||
return (this.clientTemplate.address[fieldName].find((fieldObj: any) => fieldObj.id === fieldId));
|
||||
}
|
||||
|
||||
/**
|
||||
* Utilized in address preview to check if field is enabled in configuration.
|
||||
* @param {any} fieldName Field Name
|
||||
*/
|
||||
isFieldEnabled(fieldName: any) {
|
||||
return (this.clientAddressFieldConfig.find((fieldObj: any) => fieldObj.field === fieldName)).is_enabled;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -23,6 +23,7 @@ import { ClientActionsComponent } from './clients-view/client-actions/client-act
|
||||
import { ViewChargeComponent } from './clients-view/charges/view-charge/view-charge.component';
|
||||
import { ClientPayChargesComponent } from './clients-view/charges/client-pay-charges/client-pay-charges.component';
|
||||
import { EditClientComponent } from './edit-client/edit-client.component';
|
||||
import { CreateClientComponent } from './create-client/create-client.component';
|
||||
|
||||
/** Custom Resolvers */
|
||||
import { ClientViewResolver } from './common-resolvers/client-view.resolver';
|
||||
@@ -55,7 +56,16 @@ const routes: Routes = [
|
||||
children: [
|
||||
{
|
||||
path: '',
|
||||
component: ClientsComponent,
|
||||
component: ClientsComponent
|
||||
},
|
||||
{
|
||||
path: 'create',
|
||||
data: { title: extract('Create Client'), breadcrumb: 'Create Client', routeParamBreadcrumb: false },
|
||||
component: CreateClientComponent,
|
||||
resolve: {
|
||||
clientAddressFieldConfig: ClientAddressFieldConfigurationResolver,
|
||||
clientTemplate: ClientTemplateResolver
|
||||
}
|
||||
},
|
||||
{
|
||||
path: ':clientId',
|
||||
|
||||
@@ -8,10 +8,10 @@
|
||||
</mat-checkbox>
|
||||
</div>
|
||||
<div class="action-button" fxLayoutGap="25px">
|
||||
<button mat-raised-button color="primary" [routerLink]="['./import']">
|
||||
<button mat-raised-button color="primary" [routerLink]="['import']">
|
||||
<fa-icon icon="download"></fa-icon> Import Client
|
||||
</button>
|
||||
<button mat-raised-button color="primary" [routerLink]="['./add']">
|
||||
<button mat-raised-button color="primary" [routerLink]="['create']">
|
||||
<fa-icon icon="plus"></fa-icon> Create Client
|
||||
</button>
|
||||
</div>
|
||||
@@ -65,7 +65,6 @@
|
||||
<td mat-cell *matCellDef="let row"> {{row.officeName}} </td>
|
||||
</ng-container>
|
||||
|
||||
|
||||
<!-- ID Column -->
|
||||
<ng-container matColumnDef="staff">
|
||||
<th mat-header-cell *matHeaderCellDef mat-sort-header='staffName'> StaffName </th>
|
||||
|
||||
@@ -50,6 +50,12 @@ import { DeleteSignatureDialogComponent } from './clients-view/custom-dialogs/de
|
||||
import { UploadImageDialogComponent } from './clients-view/custom-dialogs/upload-image-dialog/upload-image-dialog.component';
|
||||
import { ClientScreenReportsComponent } from './clients-view/client-actions/client-screen-reports/client-screen-reports.component';
|
||||
import { EditClientComponent } from './edit-client/edit-client.component';
|
||||
import { CreateClientComponent } from './create-client/create-client.component';
|
||||
import { ClientGeneralStepComponent } from './client-stepper/client-general-step/client-general-step.component';
|
||||
import { ClientFamilyMembersStepComponent } from './client-stepper/client-family-members-step/client-family-members-step.component';
|
||||
import { ClientPreviewStepComponent } from './client-stepper/client-preview-step/client-preview-step.component';
|
||||
import { ClientAddressStepComponent } from './client-stepper/client-address-step/client-address-step.component';
|
||||
import { ClientFamilyMemberDialogComponent } from './client-stepper/client-family-members-step/client-family-member-dialog/client-family-member-dialog.component';
|
||||
|
||||
|
||||
/**
|
||||
@@ -105,7 +111,13 @@ import { EditClientComponent } from './edit-client/edit-client.component';
|
||||
DeleteSignatureDialogComponent,
|
||||
UploadImageDialogComponent,
|
||||
ClientScreenReportsComponent,
|
||||
EditClientComponent
|
||||
EditClientComponent,
|
||||
CreateClientComponent,
|
||||
ClientGeneralStepComponent,
|
||||
ClientFamilyMembersStepComponent,
|
||||
ClientPreviewStepComponent,
|
||||
ClientAddressStepComponent,
|
||||
ClientFamilyMemberDialogComponent
|
||||
],
|
||||
entryComponents: [
|
||||
UploadDocumentDialogComponent,
|
||||
@@ -114,7 +126,8 @@ import { EditClientComponent } from './edit-client/edit-client.component';
|
||||
ViewSignatureDialogComponent,
|
||||
UploadSignatureDialogComponent,
|
||||
DeleteSignatureDialogComponent,
|
||||
UploadImageDialogComponent
|
||||
UploadImageDialogComponent,
|
||||
ClientFamilyMemberDialogComponent
|
||||
],
|
||||
providers: [DatePipe]
|
||||
|
||||
|
||||
@@ -45,6 +45,10 @@ export class ClientsService {
|
||||
return this.http.get(`/clients/${clientId}`);
|
||||
}
|
||||
|
||||
createClient(client: any) {
|
||||
return this.http.post(`/clients`, client);
|
||||
}
|
||||
|
||||
updateClient(clientId: string, client: any) {
|
||||
return this.http.put(`/clients/${clientId}`, client);
|
||||
}
|
||||
|
||||
@@ -0,0 +1,68 @@
|
||||
<div class="container">
|
||||
|
||||
<mat-horizontal-stepper class="mat-elevation-z8" labelPosition="bottom" #clientStepper>
|
||||
|
||||
<ng-template matStepperIcon="number">
|
||||
<fa-icon icon="pencil-alt" size="sm"></fa-icon>
|
||||
</ng-template>
|
||||
|
||||
<ng-template matStepperIcon="edit">
|
||||
<fa-icon icon="pencil-alt" size="sm"></fa-icon>
|
||||
</ng-template>
|
||||
|
||||
<ng-template matStepperIcon="done">
|
||||
<fa-icon icon="check" size="sm"></fa-icon>
|
||||
</ng-template>
|
||||
|
||||
<ng-template matStepperIcon="error">
|
||||
<fa-icon icon="exclamation-triangle" size="lg"></fa-icon>
|
||||
</ng-template>
|
||||
|
||||
<ng-template matStepperIcon="preview">
|
||||
<fa-icon icon="eye" size="sm"></fa-icon>
|
||||
</ng-template>
|
||||
|
||||
<mat-step [stepControl]="clientGeneralForm">
|
||||
|
||||
<ng-template matStepLabel>GENERAL</ng-template>
|
||||
|
||||
<mifosx-client-general-step [clientTemplate]="clientTemplate"></mifosx-client-general-step>
|
||||
|
||||
</mat-step>
|
||||
|
||||
<mat-step>
|
||||
|
||||
<ng-template matStepLabel>FAMILY MEMBERS</ng-template>
|
||||
|
||||
<mifosx-client-family-members-step [clientTemplate]="clientTemplate"></mifosx-client-family-members-step>
|
||||
|
||||
</mat-step>
|
||||
|
||||
<mat-step>
|
||||
|
||||
<ng-template matStepLabel>ADDRESS</ng-template>
|
||||
|
||||
<mifosx-client-address-step
|
||||
[clientTemplate]="clientTemplate"
|
||||
[clientAddressFieldConfig]="clientAddressFieldConfig"
|
||||
>
|
||||
</mifosx-client-address-step>
|
||||
|
||||
</mat-step>
|
||||
|
||||
<mat-step *ngIf="clientGeneralForm.valid" completed>
|
||||
|
||||
<ng-template matStepLabel>PREVIEW</ng-template>
|
||||
|
||||
<mifosx-client-preview-step
|
||||
[clientTemplate]="clientTemplate"
|
||||
[clientAddressFieldConfig]="clientAddressFieldConfig"
|
||||
[client]="client" (submit)="submit()"
|
||||
>
|
||||
</mifosx-client-preview-step>
|
||||
|
||||
</mat-step>
|
||||
|
||||
</mat-horizontal-stepper>
|
||||
|
||||
</div>
|
||||
@@ -0,0 +1,25 @@
|
||||
import { async, ComponentFixture, TestBed } from '@angular/core/testing';
|
||||
|
||||
import { CreateClientComponent } from './create-client.component';
|
||||
|
||||
describe('CreateClientComponent', () => {
|
||||
let component: CreateClientComponent;
|
||||
let fixture: ComponentFixture<CreateClientComponent>;
|
||||
|
||||
beforeEach(async(() => {
|
||||
TestBed.configureTestingModule({
|
||||
declarations: [ CreateClientComponent ]
|
||||
})
|
||||
.compileComponents();
|
||||
}));
|
||||
|
||||
beforeEach(() => {
|
||||
fixture = TestBed.createComponent(CreateClientComponent);
|
||||
component = fixture.componentInstance;
|
||||
fixture.detectChanges();
|
||||
});
|
||||
|
||||
it('should create', () => {
|
||||
expect(component).toBeTruthy();
|
||||
});
|
||||
});
|
||||
@@ -0,0 +1,84 @@
|
||||
/** Angular Imports */
|
||||
import { Component, ViewChild } from '@angular/core';
|
||||
import { Router, ActivatedRoute } from '@angular/router';
|
||||
|
||||
/** Custom Services */
|
||||
import { ClientsService } from '../clients.service';
|
||||
|
||||
/** Custom Components */
|
||||
import { ClientGeneralStepComponent } from '../client-stepper/client-general-step/client-general-step.component';
|
||||
import { ClientFamilyMembersStepComponent } from '../client-stepper/client-family-members-step/client-family-members-step.component';
|
||||
import { ClientAddressStepComponent } from '../client-stepper/client-address-step/client-address-step.component';
|
||||
|
||||
/**
|
||||
* Create Client Component.
|
||||
*/
|
||||
@Component({
|
||||
selector: 'mifosx-create-client',
|
||||
templateUrl: './create-client.component.html',
|
||||
styleUrls: ['./create-client.component.scss']
|
||||
})
|
||||
export class CreateClientComponent {
|
||||
|
||||
/** Client General Step */
|
||||
@ViewChild(ClientGeneralStepComponent) clientGeneralStep: ClientGeneralStepComponent;
|
||||
/** Client Family Members Step */
|
||||
@ViewChild(ClientFamilyMembersStepComponent) clientFamilyMembersStep: ClientFamilyMembersStepComponent;
|
||||
/** Client Address Step */
|
||||
@ViewChild(ClientAddressStepComponent) clientAddressStep: ClientAddressStepComponent;
|
||||
|
||||
/** Client Template */
|
||||
clientTemplate: any;
|
||||
/** Client Address Field Config */
|
||||
clientAddressFieldConfig: any;
|
||||
|
||||
/**
|
||||
* Fetches client and address template from `resolve`
|
||||
* @param {ActivatedRoute} route Activated Route
|
||||
* @param {Router} router Router
|
||||
* @param {ClientsService} clientsService Clients Service
|
||||
*/
|
||||
constructor(private route: ActivatedRoute,
|
||||
private router: Router,
|
||||
private clientsService: ClientsService) {
|
||||
this.route.data.subscribe((data: { clientTemplate: any, clientAddressFieldConfig: any }) => {
|
||||
this.clientTemplate = data.clientTemplate;
|
||||
this.clientAddressFieldConfig = data.clientAddressFieldConfig;
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Retrieves general information about client.
|
||||
*/
|
||||
get clientGeneralForm() {
|
||||
return this.clientGeneralStep.createClientForm;
|
||||
}
|
||||
|
||||
/**
|
||||
* Retrieves the client object
|
||||
*/
|
||||
get client() {
|
||||
return {
|
||||
...this.clientGeneralStep.clientGeneralDetails,
|
||||
...this.clientFamilyMembersStep.familyMembers,
|
||||
...this.clientAddressStep.address
|
||||
};
|
||||
}
|
||||
/**
|
||||
* Submits the create client form.
|
||||
*/
|
||||
submit() {
|
||||
const locale = 'en';
|
||||
const dateFormat = 'dd MMMM yyyy';
|
||||
// TODO: Update once language and date settings are setup
|
||||
const clientData = {
|
||||
...this.client,
|
||||
dateFormat,
|
||||
locale
|
||||
};
|
||||
this.clientsService.createClient(clientData).subscribe((response: any) => {
|
||||
this.router.navigate(['../', response.resourceId], { relativeTo: this.route });
|
||||
});
|
||||
}
|
||||
|
||||
}
|
||||
Reference in New Issue
Block a user