diff --git a/FrontEnd/package.json b/FrontEnd/package.json
index 260fa5f..f701bf9 100644
--- a/FrontEnd/package.json
+++ b/FrontEnd/package.json
@@ -41,6 +41,7 @@
"popper.js": "^1.12.9",
"primeicons": "^1.0.0",
"primeng": "^6.1.7",
+ "ngx-csv": "^0.3.1",
"rxjs": "^5.5.2",
"zone.js": "^0.8.14"
},
diff --git a/FrontEnd/src/app/app-routing.module.ts b/FrontEnd/src/app/app-routing.module.ts
index b9a7e19..0b1ce1e 100644
--- a/FrontEnd/src/app/app-routing.module.ts
+++ b/FrontEnd/src/app/app-routing.module.ts
@@ -46,6 +46,7 @@ import { BagdesComponent } from './user/bagdes/bagdes.component';
import { RankingComponent } from './groups/ranking/ranking.component';
import { HistoryOfActivityInGroupComponent } from './groups/history-of-activity-in-group/history-of-activity-in-group.component';
import { LoginUsosComponent } from './login/login-usos/login-usos.component';
+import { TestsInGroupResultsComponent } from './groups/tests-in-group-results/tests-in-group-results.component';
const routes: Routes = [
@@ -87,7 +88,8 @@ const routes: Routes = [
{ path: 'groups/ranking/:id', component: RankingComponent , canActivate: [AuthGuard] },
{ path: 'groups/waiting-resources/:id', component: WaitingResourcesComponent, canActivate: [AuthGuard] },
{ path: 'groups/waiting-resources/:id', component: WaitingResourcesComponent, canActivate: [AuthGuard] },
- { path: 'groups/history/:id', component: HistoryOfActivityInGroupComponent, canActivate: [AuthGuard] }
+ { path: 'groups/history/:id', component: HistoryOfActivityInGroupComponent, canActivate: [AuthGuard] },
+ { path: 'groups/tests-results/:id', component: TestsInGroupResultsComponent, canActivate: [AuthGuard] }
];
@NgModule({
diff --git a/FrontEnd/src/app/groups/group-details/group-details.component.html b/FrontEnd/src/app/groups/group-details/group-details.component.html
index 9881f36..77fff7f 100644
--- a/FrontEnd/src/app/groups/group-details/group-details.component.html
+++ b/FrontEnd/src/app/groups/group-details/group-details.component.html
@@ -6,6 +6,9 @@
+
+
diff --git a/FrontEnd/src/app/groups/group-details/group-details.component.ts b/FrontEnd/src/app/groups/group-details/group-details.component.ts
index 0670d8a..2bf54a4 100644
--- a/FrontEnd/src/app/groups/group-details/group-details.component.ts
+++ b/FrontEnd/src/app/groups/group-details/group-details.component.ts
@@ -249,6 +249,10 @@ export class GroupDetailsComponent implements OnInit, OnDestroy {
this.router.navigate(['groups/ranking', this.id]);
}
+ goToTestsResults() {
+ this.router.navigate(['groups/tests-results', this.id]);
+ }
+
goToHistory() {
this.router.navigate(['groups/history', this.id]);
}
diff --git a/FrontEnd/src/app/groups/group.ts b/FrontEnd/src/app/groups/group.ts
index f9a5516..fc4290e 100644
--- a/FrontEnd/src/app/groups/group.ts
+++ b/FrontEnd/src/app/groups/group.ts
@@ -30,3 +30,20 @@ export class ActivityHistory {
constructor() {}
}
+
+export class TestsInGroup {
+ public id: number;
+ public title: string;
+ public maxScore: number;
+
+ constructor() {}
+}
+
+export class TestsInGroupResults {
+ public name: string;
+ public surname: string;
+ public userScore: number;
+ public percent: number;
+
+ constructor() {}
+}
diff --git a/FrontEnd/src/app/groups/groups.module.ts b/FrontEnd/src/app/groups/groups.module.ts
index 9a2d1b5..9657517 100644
--- a/FrontEnd/src/app/groups/groups.module.ts
+++ b/FrontEnd/src/app/groups/groups.module.ts
@@ -30,6 +30,7 @@ import { MaterialToGroupPreviewComponent } from './waiting-resources/material-to
import { FlashcardsToGroupPreviewComponent } from './waiting-resources/flashcards-to-group-preview/flashcards-to-group-preview.component';
import { RankingComponent } from './ranking/ranking.component';
import { HistoryOfActivityInGroupComponent } from './history-of-activity-in-group/history-of-activity-in-group.component';
+import { TestsInGroupResultsComponent } from './tests-in-group-results/tests-in-group-results.component';
@NgModule({
@@ -63,7 +64,8 @@ import { HistoryOfActivityInGroupComponent } from './history-of-activity-in-grou
MaterialToGroupPreviewComponent,
FlashcardsToGroupPreviewComponent,
RankingComponent,
- HistoryOfActivityInGroupComponent
+ HistoryOfActivityInGroupComponent,
+ TestsInGroupResultsComponent
],
providers: [GroupsService, ConfirmationService]
diff --git a/FrontEnd/src/app/groups/groups.service.ts b/FrontEnd/src/app/groups/groups.service.ts
index 33a1a4a..97a9b78 100644
--- a/FrontEnd/src/app/groups/groups.service.ts
+++ b/FrontEnd/src/app/groups/groups.service.ts
@@ -28,6 +28,9 @@ export class GroupsService {
private getActivityHistoryURL = 'groups/{groupId}/users/activity?sort={sort}';
+ private getTestsInGroupsURL = 'groups/{groupId}/tests';
+ private getResultsInTestsURL = 'groups/{groupId}/tests/{testId}/results';
+
constructor(private httpClient: HttpClient, private authenticationService: AuthenticationService) {
this.setHeaders();
}
@@ -45,6 +48,18 @@ export class GroupsService {
}
}
+ getTestsInGroups(groupId: number): Observable {
+ this.setHeaders();
+ const url = this.getTestsInGroupsURL.replace('{groupId}', groupId.toString());
+ return this.httpClient.get(url, { headers: this.headers });
+ }
+
+ getResultsInTests(groupId: number, testId: number): Observable {
+ this.setHeaders();
+ const url = this.getResultsInTestsURL.replace('{groupId}', groupId.toString()).replace('{testId}', testId.toString());
+ return this.httpClient.get(url, { headers: this.headers });
+ }
+
getGroups(): Observable {
this.setHeaders();
const url = this.getGroupsURL;
diff --git a/FrontEnd/src/app/groups/tests-in-group-results/tests-in-group-results.component.css b/FrontEnd/src/app/groups/tests-in-group-results/tests-in-group-results.component.css
new file mode 100644
index 0000000..722b21b
--- /dev/null
+++ b/FrontEnd/src/app/groups/tests-in-group-results/tests-in-group-results.component.css
@@ -0,0 +1,24 @@
+.wrapper{
+ width: 100%;
+ padding: 30px;
+ min-height: 100%;
+ margin-bottom: 40px;
+}
+
+.content{
+ background-color: #181616;
+ padding: 30px;
+ margin-top: 2rem;
+ margin-bottom: 2rem;
+ text-align: center;
+ margin-left: auto;
+ margin-right: auto;
+}
+
+ag-grid-angular{
+ margin: 10px;
+}
+
+.buttons-container > div{
+ margin: 10px;
+}
diff --git a/FrontEnd/src/app/groups/tests-in-group-results/tests-in-group-results.component.html b/FrontEnd/src/app/groups/tests-in-group-results/tests-in-group-results.component.html
new file mode 100644
index 0000000..41b0b55
--- /dev/null
+++ b/FrontEnd/src/app/groups/tests-in-group-results/tests-in-group-results.component.html
@@ -0,0 +1,28 @@
+
+
+
{{group?.name}}
+
+
+
Wybierz test aby zobaczyć wyniki:
+
+
+
+
+
+
+
Wybrany test: {{selectedTest.title}}
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/FrontEnd/src/app/groups/tests-in-group-results/tests-in-group-results.component.spec.ts b/FrontEnd/src/app/groups/tests-in-group-results/tests-in-group-results.component.spec.ts
new file mode 100644
index 0000000..565ba78
--- /dev/null
+++ b/FrontEnd/src/app/groups/tests-in-group-results/tests-in-group-results.component.spec.ts
@@ -0,0 +1,25 @@
+import { async, ComponentFixture, TestBed } from '@angular/core/testing';
+
+import { TestsInGroupResultsComponent } from './tests-in-group-results.component';
+
+describe('TestsInGroupResultsComponent', () => {
+ let component: TestsInGroupResultsComponent;
+ let fixture: ComponentFixture;
+
+ beforeEach(async(() => {
+ TestBed.configureTestingModule({
+ declarations: [ TestsInGroupResultsComponent ]
+ })
+ .compileComponents();
+ }));
+
+ beforeEach(() => {
+ fixture = TestBed.createComponent(TestsInGroupResultsComponent);
+ component = fixture.componentInstance;
+ fixture.detectChanges();
+ });
+
+ it('should create', () => {
+ expect(component).toBeTruthy();
+ });
+});
diff --git a/FrontEnd/src/app/groups/tests-in-group-results/tests-in-group-results.component.ts b/FrontEnd/src/app/groups/tests-in-group-results/tests-in-group-results.component.ts
new file mode 100644
index 0000000..507de21
--- /dev/null
+++ b/FrontEnd/src/app/groups/tests-in-group-results/tests-in-group-results.component.ts
@@ -0,0 +1,189 @@
+import { Component, OnInit, OnDestroy } from '@angular/core';
+import { ActivatedRoute } from '@angular/router';
+import { GroupsService } from '../groups.service';
+import { Group, TestsInGroup, TestsInGroupResults } from '../group';
+import { Subscription } from 'rxjs/Subscription';
+import localeText from './../../../assets/localeText';
+import { GridOptions, RowDoubleClickedEvent } from 'ag-grid-community/main';
+import { MatSnackBar } from '@angular/material';
+
+import { ngxCsv } from 'ngx-csv/ngx-csv';
+
+
+@Component({
+ selector: 'app-tests-in-group-results',
+ templateUrl: './tests-in-group-results.component.html',
+ styleUrls: ['./tests-in-group-results.component.css']
+})
+export class TestsInGroupResultsComponent implements OnInit, OnDestroy {
+
+ id: number;
+ currentUser;
+ subs: Subscription[] = [];
+ public group: Group;
+ public selectedTest: TestsInGroup;
+
+ public localeText = localeText;
+
+ // chooseTests
+ public data: TestsInGroup[] = [];
+ public gridApi;
+ public gridOptions: GridOptions;
+ public columnDefs = [
+ { headerName: 'ID', field: 'id', headerTooltip: 'ID' },
+ { headerName: 'Nazwa', field: 'title', headerTooltip: 'Nazwa' },
+ { headerName: 'Liczba punktów do zdobycia', field: 'maxScore', headerTooltip: 'Liczba punktów do zdobycia', hide: false }
+ ];
+
+ // showTestResult
+ public testdata: TestsInGroupResults[] = [];
+ public testgridApi;
+ public testgridOptions: GridOptions;
+ public testcolumnDefs = [
+ { headerName: 'Imię', field: 'name', headerTooltip: 'Imię' },
+ { headerName: 'Nazwisko', field: 'surname', headerTooltip: 'Nazwisko' },
+ { headerName: 'Wynik', field: 'userScore', headerTooltip: 'Wynik', hide: false },
+ { headerName: 'Wynik (%)', field: 'percent', headerTooltip: 'Wynik (%)', hide: false }
+ ];
+
+ constructor(private route: ActivatedRoute,
+ private groupService: GroupsService,
+ public snackBar: MatSnackBar) { }
+
+ ngOnInit() {
+ this.id = this.route.snapshot.params.id;
+ this.currentUser = JSON.parse(localStorage.getItem('currentUser'));
+ this.subs.push(
+ this.groupService.getGroupDetails(this.id)
+ .subscribe(
+ data => {
+ this.group = data;
+ this.getTests();
+ localStorage.setItem('groupOwnerUsername', this.group.owner);
+ }
+ )
+ );
+
+ this.gridOptions = {
+ rowHeight: 50,
+ headerHeight: 25,
+ getRowStyle: function (params) {
+ return {
+ cursor: 'pointer'
+ };
+ },
+ };
+
+ this.testgridOptions = {
+ rowHeight: 50,
+ headerHeight: 25,
+ getRowStyle: function (params) {
+ return {
+ cursor: 'pointer'
+ };
+ },
+ };
+ }
+
+ getTests() {
+ this.subs.push(this.groupService.getTestsInGroups(this.id).subscribe(
+ success => {
+ this.data = success;
+ },
+ error => {
+ console.log(error);
+ this.snackBar.open('Nie udało się załadować listy testów!', null,
+ { duration: 3000, verticalPosition: 'top', panelClass: ['snackbar-error'] });
+ }
+ ));
+ }
+
+ goTo(event: RowDoubleClickedEvent) {
+ this.selectedTest = event.data;
+ this.getResults(event.data.id);
+ }
+
+ downloadCSVResults() {
+ // tslint:disable-next-line:no-unused-expression
+ new ngxCsv(this.testdata, this.selectedTest.title + '_wyniki');
+ }
+
+ getResults(id: number) {
+ this.subs.push(this.groupService.getResultsInTests(this.id, id).subscribe(
+ success => {
+ this.testdata = success;
+ },
+ error => {
+ console.log(error);
+ this.snackBar.open('Nie udało się załadować wyników za test!', null,
+ { duration: 3000, verticalPosition: 'top', panelClass: ['snackbar-error'] });
+ }
+ ));
+ }
+
+ ngOnDestroy() {
+ if (this.subs) {
+ this.subs.forEach(x => x.unsubscribe());
+ }
+
+ localStorage.removeItem('groupOwnerUsername');
+ }
+
+ // chooseTests
+ public onRowClicked(e) {
+ if (e.event.target !== undefined) {
+ this.goTo(e);
+ }
+ }
+
+ onGridReady(params) {
+ this.gridApi = params.api;
+ this.gridApi.sizeColumnsToFit();
+ }
+
+ onGridColumnsChanged(params) {
+ params.api.sizeColumnsToFit();
+ }
+
+ onGridSizeChanged(params) {
+ this.columnDefs = [
+ { headerName: 'ID', field: 'id', headerTooltip: 'ID' },
+ { headerName: 'Nazwa', field: 'title', headerTooltip: 'Nazwa' },
+ { headerName: 'Liczba punktów do zdobycia', field: 'maxScore', headerTooltip: 'Liczba punktów do zdobycia', hide: false }
+ ];
+
+ params.api.sizeColumnsToFit();
+ }
+
+ onGidColumnsChanged(params) {
+ params.api.sizeColumnsToFit();
+ }
+
+ // showTestResult
+ public testonRowClicked(e) {}
+
+ testonGridReady(params) {
+ this.testgridApi = params.api;
+ this.testgridApi.sizeColumnsToFit();
+ }
+
+ testonGridColumnsChanged(params) {
+ params.api.sizeColumnsToFit();
+ }
+
+ testonGridSizeChanged(params) {
+ this.testcolumnDefs = [
+ { headerName: 'Imię', field: 'name', headerTooltip: 'Imię' },
+ { headerName: 'Nazwisko', field: 'surname', headerTooltip: 'Nazwisko' },
+ { headerName: 'Wynik', field: 'userScore', headerTooltip: 'Wynik', hide: false },
+ { headerName: 'Wynik (%)', field: 'percent', headerTooltip: 'Wynik (%)', hide: false }
+ ];
+
+ params.api.sizeColumnsToFit();
+ }
+
+ testonGidColumnsChanged(params) {
+ params.api.sizeColumnsToFit();
+ }
+
+}
diff --git a/FrontEnd/src/assets/localeText.ts b/FrontEnd/src/assets/localeText.ts
index 36df79e..6c291e9 100644
--- a/FrontEnd/src/assets/localeText.ts
+++ b/FrontEnd/src/assets/localeText.ts
@@ -49,7 +49,7 @@ const localeText = {
toolPanelButton: 'Narzędzia',
// other
- noRowsToShow: 'Brak testów do wyświetlenia',
+ noRowsToShow: 'Brak elementów do wyświetlenia',
// enterprise menu
pinColumn: 'Przypiąta kolumna',