Skip to content

Commit

Permalink
fix: improved usability of assigning children to a school/group
Browse files Browse the repository at this point in the history
  • Loading branch information
christophscheuing authored Jan 19, 2022
1 parent e3de800 commit 9dec0d6
Show file tree
Hide file tree
Showing 38 changed files with 780 additions and 451 deletions.
2 changes: 2 additions & 0 deletions src/app/child-dev-project/children/children.module.ts
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,7 @@ import { MatSnackBarModule } from "@angular/material/snack-bar";
import { MatSortModule } from "@angular/material/sort";
import { MatTableModule } from "@angular/material/table";
import { MatTooltipModule } from "@angular/material/tooltip";
import { MatChipsModule } from "@angular/material/chips";
import { FlexLayoutModule } from "@angular/flex-layout";
import { ChildrenService } from "./children.service";
import { ChildrenCountDashboardComponent } from "./children-count-dashboard/children-count-dashboard.component";
Expand Down Expand Up @@ -91,6 +92,7 @@ import { FontAwesomeModule } from "@fortawesome/angular-fontawesome";
MatProgressBarModule,
MatAutocompleteModule,
MatTooltipModule,
MatChipsModule,
BrowserAnimationsModule,
ReactiveFormsModule,
FilterPipeModule,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -99,6 +99,13 @@ describe("ChildSchoolRelation Entity", () => {
expect(relation.isActive).toBeTrue();
});

it("should mark relation with end date being today as active", () => {
const relation = new ChildSchoolRelation();
relation.start = moment().subtract(1, "week").toDate();
relation.end = new Date();
expect(relation.isActive).toBeTrue();
});

it("should fail validation when end date but no start date is defined", () => {
const relation = new ChildSchoolRelation();
relation.schoolId = "someId";
Expand Down
10 changes: 7 additions & 3 deletions src/app/child-dev-project/children/model/childSchoolRelation.ts
Original file line number Diff line number Diff line change
Expand Up @@ -30,13 +30,13 @@ export class ChildSchoolRelation extends Entity {
schoolClass: string = "";
@DatabaseField({
dataType: "date-only",
label: $localize`:Label for the start date of a relation:From`,
label: $localize`:Label for the start date of a relation:Start date`,
description: $localize`:Description of the start date of a relation:The date a child joins a school`,
})
start: Date;
@DatabaseField({
dataType: "date-only",
label: $localize`:Label for the end date of a relation:To`,
label: $localize`:Label for the end date of a relation:End date`,
description: $localize`:Description of the end date of a relation:The date of a child leaving the school`,
})
end: Date;
Expand All @@ -53,10 +53,14 @@ export class ChildSchoolRelation extends Entity {
return (
this.start &&
moment(this.start).isSameOrBefore(moment(), "day") &&
(!this.end || moment(this.end).isAfter(moment(), "day"))
(!this.end || moment(this.end).isSameOrAfter(moment(), "day"))
);
}

getColor(): string {
return this.isActive ? "#90ee9040" : "";
}

assertValid() {
super.assertValid();
const startLabel = this.getSchema().get("start").label;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,14 @@ export const heightRangeForAge = new Map<number, any>([
[13.5, { min: 146, max: 171 }],
[14, { min: 148, max: 172 }],
[14.5, { min: 148, max: 173 }],
[15, { min: 150, max: 174 }],
[15.5, { min: 152, max: 174 }],
[16, { min: 154, max: 175 }],
[16.5, { min: 156, max: 176 }],
[17, { min: 158, max: 177 }],
[17.5, { min: 158, max: 177 }],
[18, { min: 158, max: 177 }],
[18.5, { min: 158, max: 177 }],
]);

export const weightRangeForAge = new Map<number, any>([
Expand Down Expand Up @@ -56,4 +64,12 @@ export const weightRangeForAge = new Map<number, any>([
[13.5, { min: 34, max: 74 }],
[14, { min: 36, max: 77 }],
[14.5, { min: 38, max: 79 }],
[15, { min: 40, max: 80 }],
[15.5, { min: 42, max: 85 }],
[16, { min: 44, max: 90 }],
[16.5, { min: 46, max: 95 }],
[17, { min: 48, max: 100 }],
[17.5, { min: 48, max: 100 }],
[18, { min: 48, max: 100 }],
[18.5, { min: 48, max: 100 }],
]);
Original file line number Diff line number Diff line change
Expand Up @@ -29,12 +29,22 @@ export class HealthCheckupComponent
id: "bmi",
label: $localize`:Table header, Short for Body Mass Index:BMI`,
view: "ReadonlyFunction",
additional: (entity: HealthCheck) => entity.bmi.toFixed(2),
tooltip: $localize`:Tooltip for BMI info:This is calculated using the height and the weight measure`,
additional: (entity: HealthCheck) => this.getBMI(entity),
},
];
@Input() child: Child;
constructor(private childrenService: ChildrenService) {}

private getBMI(healthCheck: HealthCheck): string {
const bmi = healthCheck.bmi;
if (Number.isNaN(bmi)) {
return "-";
} else {
return bmi.toFixed(2);
}
}

ngOnChanges(changes: SimpleChanges): void {
if (changes.hasOwnProperty("child")) {
this.loadData(this.child.getId());
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -59,4 +59,12 @@ export class HealthCheck extends Entity {
return WarningLevel.WARNING;
}
}

getColor(): string {
if (!this.height) {
return "#DEDEDE";
} else {
return super.getColor();
}
}
}
Original file line number Diff line number Diff line change
@@ -1,19 +1,21 @@
<div *ngIf="single && current">
<em
i18n-matTooltip
matTooltip="To change this field, please add a new entry to the history below"
i18n="
The class and school a child is currently attending|Context 'currently
attending class at school'
"
>
Currently attending class {{ current.schoolClass }}
<ng-container *ngIf="current.schoolClass">at </ng-container>
<app-school-block [entityId]="current.schoolId"></app-school-block>
</em>
</div>
<mat-chip-list *ngIf="!hasCurrentlyActiveEntry">
<mat-chip >
<span i18n="Explanation for missing currently active entry - part 1 of 2">Currently there is no active entry. To add a new entry, click on the</span>
&nbsp;
<fa-icon
class="table-action-icon"
aria-label="add"
icon="plus-circle"
style="color: #448aff;"
(click)="entitySubrecord.create()"
> </fa-icon>
&nbsp;
<span i18n="Explanation for missing currently active entry - part 2 of 2:">button</span>.
</mat-chip>
</mat-chip-list>

<app-entity-subrecord
#entitySubrecord
[records]="records"
[columns]="columns"
[newRecordFactory]="generateNewRecordFactory()"
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,10 @@ import { PanelConfig } from "../../core/entity-components/entity-details/EntityD
import { ChildSchoolRelation } from "../children/model/childSchoolRelation";
import moment from "moment";
import { MockSessionModule } from "../../core/session/mock-session.module";
import { FontAwesomeTestingModule } from "@fortawesome/angular-fontawesome/testing";
import { EntityMapperService } from "../../core/entity/entity-mapper.service";
import { Subject } from "rxjs";
import { UpdatedEntity } from "../../core/entity/model/entity-update";

describe("PreviousSchoolsComponent", () => {
let component: PreviousSchoolsComponent;
Expand All @@ -40,6 +44,7 @@ describe("PreviousSchoolsComponent", () => {
ChildrenModule,
ConfirmationDialogModule,
MockSessionModule.withState(),
FontAwesomeTestingModule,
],
providers: [
{ provide: ChildrenService, useValue: mockChildrenService },
Expand Down Expand Up @@ -69,7 +74,7 @@ describe("PreviousSchoolsComponent", () => {
);
}));

it("should only show columns which are defined by the config", fakeAsync(() => {
it("should allow to change the columns to be displayed by the config", fakeAsync(() => {
const config: PanelConfig = {
entity: new Child(),
config: {
Expand All @@ -83,11 +88,13 @@ describe("PreviousSchoolsComponent", () => {
};
component.onInitFromDynamicConfig(config);
tick();
expect(component.columns).toHaveSize(3);

let columnNames = component.columns.map((column) => column.label);
expect(columnNames).toContain("Team");
expect(columnNames).toContain("From");
expect(columnNames).toContain("To");
expect(columnNames).not.toContain("Class");
expect(columnNames).not.toContain("Result");

config.config.columns.push({
id: "schoolClass",
Expand All @@ -102,7 +109,7 @@ describe("PreviousSchoolsComponent", () => {

component.onInitFromDynamicConfig(config);
tick();
expect(component.columns).toHaveSize(5);

columnNames = component.columns.map((column) => column.label);
expect(columnNames).toContain("Team");
expect(columnNames).toContain("From");
Expand All @@ -128,4 +135,20 @@ describe("PreviousSchoolsComponent", () => {
.isSame(newRelation.start, "day")
).toBeTrue();
});

it("should reload data when a new record is saved", fakeAsync(() => {
const updateSubject = new Subject<UpdatedEntity<ChildSchoolRelation>>();
const entityMapper = TestBed.inject(EntityMapperService);
spyOn(entityMapper, "receiveUpdates").and.returnValue(updateSubject);
component.onInitFromDynamicConfig({ entity: testChild });
tick();
mockChildrenService.getSchoolRelationsFor.calls.reset();

updateSubject.next();
tick();

expect(mockChildrenService.getSchoolRelationsFor).toHaveBeenCalledWith(
testChild.getId()
);
}));
});
Original file line number Diff line number Diff line change
Expand Up @@ -6,11 +6,15 @@ import { OnInitDynamicComponent } from "../../core/view/dynamic-components/on-in
import { PanelConfig } from "../../core/entity-components/entity-details/EntityDetailsConfig";
import { FormFieldConfig } from "../../core/entity-components/entity-form/entity-form/FormConfig";
import moment from "moment";
import { UntilDestroy, untilDestroyed } from "@ngneat/until-destroy";
import { EntityMapperService } from "app/core/entity/entity-mapper.service";
import { isActiveIndicator } from "../schools/children-overview/children-overview.component";

@Component({
selector: "app-previous-schools",
templateUrl: "./previous-schools.component.html",
})
@UntilDestroy()
export class PreviousSchoolsComponent
implements OnChanges, OnInitDynamicComponent {
@Input() child: Child;
Expand All @@ -21,12 +25,16 @@ export class PreviousSchoolsComponent
{ id: "start" },
{ id: "end" },
{ id: "result" },
isActiveIndicator,
];
current: ChildSchoolRelation;
hasCurrentlyActiveEntry: boolean;

single = true;

constructor(private childrenService: ChildrenService) {}
constructor(
private childrenService: ChildrenService,
private entityMapperService: EntityMapperService
) {}

ngOnChanges(changes: SimpleChanges) {
if (changes.hasOwnProperty("child")) {
Expand All @@ -40,9 +48,11 @@ export class PreviousSchoolsComponent
}
if (panelConfig.config?.columns) {
this.columns = panelConfig.config.columns;
this.columns.push(isActiveIndicator);
}
this.child = panelConfig.entity as Child;
this.loadData(this.child.getId());
this.subscribeToChildSchoolRelationUpdates();
}

async loadData(id: string) {
Expand All @@ -51,7 +61,9 @@ export class PreviousSchoolsComponent
}

this.records = await this.childrenService.getSchoolRelationsFor(id);
this.current = this.records.find((record) => record.isActive);
this.hasCurrentlyActiveEntry = this.records.some(
(record) => record.isActive
);
}

generateNewRecordFactory() {
Expand All @@ -67,4 +79,11 @@ export class PreviousSchoolsComponent
return newPreviousSchool;
};
}

private subscribeToChildSchoolRelationUpdates() {
this.entityMapperService
.receiveUpdates<ChildSchoolRelation>(ChildSchoolRelation)
.pipe(untilDestroyed(this))
.subscribe(() => this.loadData(this.child.getId()));
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -2,5 +2,6 @@
[records]="records"
[columns]="columns"
[newRecordFactory]="generateNewRecordFactory()"
[getBackgroundColor]="null"
></app-entity-subrecord>

Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,18 @@ import { ChildSchoolRelation } from "../../children/model/childSchoolRelation";
import { Entity } from "../../../core/entity/model/entity";
import { ChildrenService } from "../../children/children.service";

export const isActiveIndicator = {
id: "isActive",
label: $localize`:Label for the currently active status|e.g. Currently active:Currently`,
view: "ReadonlyFunction",
hideFromTable: true,
tooltip: $localize`:Tooltip for the status of currently active or not:Only added to school/group if active.Change the start or end date to modify this status.`,
additional: (csr: ChildSchoolRelation) =>
csr.isActive
? $localize`:Indication for the currently active status of an entry:active`
: $localize`:Indication for the currently inactive status of an entry:not active`,
};

/**
* This component creates a table containing all children currently attending this school.
*/
Expand All @@ -23,6 +35,7 @@ export class ChildrenOverviewComponent implements OnInitDynamicComponent {
{ id: "start" },
{ id: "end" },
{ id: "result" },
isActiveIndicator,
];

entity: Entity;
Expand Down
10 changes: 1 addition & 9 deletions src/app/core/config/config-fix.ts
Original file line number Diff line number Diff line change
Expand Up @@ -544,15 +544,7 @@ export const defaultJsonConfig = {
"title": $localize`:Title inside a panel:School History`,
"component": "PreviousSchools",
"config": {
"single": true,
"columns": [
"schoolId",
"schoolClass",
"start",
"end",
"result",
],
}
"single": true, }
},
{
"title": $localize`:Title inside a panel:ASER Results`,
Expand Down
2 changes: 1 addition & 1 deletion src/app/core/config/config-migration.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -519,7 +519,7 @@ export class ConfigMigrationService {
id: "bmi",
label: "BMI",
view: "ReadonlyFunction",
additional: (entity: HealthCheck) => entity.bmi.toFixed(2),
additional: (entity: HealthCheck) => "BMI: " + entity.bmi.toFixed(2),
},
];
config.columns = config.displayedColumns.map((col: string) => {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { Component } from "@angular/core";
import { ViewComponent } from "../../entity-components/entity-utils/view-components/view-component";
import { ViewDirective } from "../../entity-components/entity-utils/view-components/view.directive";

/**
* This component displays a text attribute.
Expand All @@ -8,4 +8,4 @@ import { ViewComponent } from "../../entity-components/entity-utils/view-compone
selector: "app-display-configurable-enum",
template: `{{ entity[property]?.label }}`,
})
export class DisplayConfigurableEnumComponent extends ViewComponent {}
export class DisplayConfigurableEnumComponent extends ViewDirective {}
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ import { PermissionsModule } from "../../permissions/permissions.module";
import { MatTooltipModule } from "@angular/material/tooltip";
import { MatFormFieldModule } from "@angular/material/form-field";
import { FontAwesomeModule } from "@fortawesome/angular-fontawesome";
import { MatChipsModule } from "@angular/material/chips";

@NgModule({
declarations: [EntityFormComponent],
Expand All @@ -21,6 +22,7 @@ import { FontAwesomeModule } from "@fortawesome/angular-fontawesome";
MatTooltipModule,
MatFormFieldModule,
FontAwesomeModule,
MatChipsModule,
],
providers: [EntityFormService],
exports: [EntityFormComponent],
Expand Down
Loading

0 comments on commit 9dec0d6

Please sign in to comment.