Create single page for statistics #5

Merged
hardi merged 1 commits from task/transform-stats-two-columns into master 2017-08-06 11:40:56 +02:00
30 changed files with 232 additions and 97 deletions

View File

@ -21,25 +21,8 @@
<li routerLinkActive="active">
<a routerLink='{{config.overviewPath}}' class="link">Armeeübersicht</a>
</li>
<li class="dropdown">
<a href="#" class="dropdown-toggle" data-toggle="dropdown" role="button" aria-haspopup="true"
aria-expanded="false">
Statistik
<span class="caret"></span>
</a>
<ul class="dropdown-menu scrollable-menu">
<li *ngIf="loginService.hasPermission(3)">
<a routerLink='{{config.warPath}}' class="link">Hinzufügen...</a>
</li>
<li>
<a routerLink='{{config.statsPath}}' class="link">Übersicht</a>
</li>
<li *ngFor="let war of wars">
<a routerLink='{{config.warPath}}/{{war._id}}'>{{war.title}}
<small>{{war.date | date: 'dd.MM.yy'}}</small>
</a>
</li>
</ul>
<li routerLinkActive="active">
<a routerLink='{{config.statsPath}}' class="link">Statistiken</a>
</li>
<li *ngIf="loginService.hasPermission(2)" routerLinkActive="active">
<a routerLink='{{config.userPath}}' class="link">Teilnehmer</a>

View File

@ -1,9 +1,7 @@
import {Component, Inject, Optional} from '@angular/core';
import {Route, Router} from '@angular/router';
import {Router} from '@angular/router';
import {LoginService} from './services/login-service/login-service';
import {AUTH_ENABLED} from './app.tokens';
import {WarService} from "./services/war-service/war.service";
import {War} from "./models/model-interfaces";
import {PromotionService} from "./services/promotion-service/promotion.service";
import {AwardingService} from "./services/awarding-service/awarding.service";
import {RouteConfig} from "./app.config";
@ -15,13 +13,10 @@ import {RouteConfig} from "./app.config";
})
export class AppComponent {
wars: War[] = [];
config = RouteConfig;
constructor(@Optional() @Inject(AUTH_ENABLED) public authEnabled,
private loginService: LoginService,
private warService: WarService,
private promotionService: PromotionService,
private awardingService: AwardingService,
private router: Router) {
@ -29,9 +24,6 @@ export class AppComponent {
ngOnInit() {
this.warService.getAllWars().subscribe((wars) => {
this.wars = wars;
});
if (this.loginService.hasPermission(2)) {
const fraction = this.loginService.getCurrentUser().squad.fraction;
this.promotionService.checkUnconfirmedPromotions(fraction);

View File

@ -28,7 +28,6 @@ export const RouteConfig = {
statsPath: 'stats',
userPath: 'users',
overviewPath: 'overview',
warPath: 'war',
requestAwardPath: 'request-award',
requestPromotionPath: 'request-promotion',
confirmAwardPath: 'confirm-award',

View File

@ -5,7 +5,7 @@ import {HttpModule} from '@angular/http';
import {AppComponent} from './app.component';
import {LoginService} from "./services/login-service/login-service";
import {UserStore} from "./services/stores/user.store";
import {ShowErrorComponent} from './show-error/show-error.component';
import {ShowErrorComponent} from './common/show-error/show-error.component';
import {APPLICATION_VALIDATORS} from './models/app-validators';
import {appRouting, routingComponents, routingProviders} from './app.routing';
import {AUTH_ENABLED} from './app.tokens';

View File

@ -1,6 +1,6 @@
import {RouterModule, Routes} from "@angular/router";
import {LoginComponent} from "./login/index";
import {NotFoundComponent} from "./not-found/not-found.component";
import {NotFoundComponent} from "./common/not-found/not-found.component";
import {LoginGuardAdmin, LoginGuardHL, LoginGuardMT, LoginGuardSQL} from "./login/login.guard";
import {usersRoutes, usersRoutingComponents} from "./users/users.routing";
import {squadsRoutes, squadsRoutingComponents} from "./squads/squads.routing";
@ -13,17 +13,15 @@ import {RequestAwardComponent} from "./request/award/req-award.component";
import {RequestPromotionComponent} from "./request/promotion/req-promotion.component";
import {ConfirmPromotionComponent} from "./request/confirm-promotion/confirm-promotion.component";
import {ConfirmAwardComponent} from "./request/confirm-award/confirm-award.component";
import {warRoutes, warsRoutingComponents} from "./wars/wars.routing";
import {StatisticComponent} from "./statistic/statistic.component";
import {RouteConfig} from "./app.config";
import {statsRoutes, statsRoutingComponents} from "./statistic/stats.routing";
export const appRoutes: Routes = [
{path: RouteConfig.overviewPath, children: armyRoutes},
{path: '', redirectTo: RouteConfig.overviewPath, pathMatch: 'full'},
{path: RouteConfig.warPath, children: warRoutes},
{path: RouteConfig.statsPath, component: StatisticComponent},
{path: RouteConfig.statsPath, children: statsRoutes},
{path: RouteConfig.loginPath, component: LoginComponent},
{path: RouteConfig.signUpPath, component: SignupComponent},
@ -48,7 +46,7 @@ export const appRoutes: Routes = [
export const appRouting = RouterModule.forRoot(appRoutes);
export const routingComponents = [LoginComponent, SignupComponent, RequestAwardComponent, RequestPromotionComponent, ConfirmAwardComponent,
ConfirmPromotionComponent, StatisticComponent, AdminComponent, ...armyRoutingComponents, NotFoundComponent, ...usersRoutingComponents,
...squadsRoutingComponents, ...decorationsRoutingComponents, ...ranksRoutingComponents, ...warsRoutingComponents];
ConfirmPromotionComponent, AdminComponent, ...armyRoutingComponents, NotFoundComponent, ...usersRoutingComponents,
...squadsRoutingComponents, ...decorationsRoutingComponents, ...ranksRoutingComponents, ...statsRoutingComponents];
export const routingProviders = [LoginGuardSQL, LoginGuardHL, LoginGuardMT, LoginGuardAdmin];

View File

@ -1,9 +1,9 @@
h3 {
width: 920px;
margin-left: 25%;
margin-left: 5%;
}
.chart-container {
width: 1200px;
margin-left: 25%;
margin-left: 5%;
}

View File

@ -1,14 +1,13 @@
import {Component} from "@angular/core";
import {AppComponent} from "../app.component";
import {WarService} from "../services/war-service/war.service";
import {WarService} from "../../services/war-service/war.service";
@Component({
selector: 'statistic',
templateUrl: './statistic.component.html',
styleUrls: ['./statistic.component.css']
selector: 'stats-overview',
templateUrl: './stats-overview.component.html',
styleUrls: ['./stats-overview.component.css']
})
export class StatisticComponent {
export class StatisticOverviewComponent {
pointData: any[] = [];
playerData: any[] = [];
@ -17,19 +16,14 @@ export class StatisticComponent {
domain: ['#0000FF', '#B22222']
};
constructor(private appComponent: AppComponent,
private warService: WarService) {
constructor(private warService: WarService) {
}
ngOnInit() {
let wars = this.appComponent.wars;
if (wars.length === 0) {
this.warService.getAllWars().subscribe(items => {
this.initChart(items);
})
}
this.initChart(wars);
}
initChart(wars: any[]) {
let pointsObj = [

View File

@ -0,0 +1,9 @@
#left {
width: 320px;
float: left;
padding-right: 10px;
}
#right {
overflow: hidden
}

View File

@ -0,0 +1 @@
<router-outlet></router-outlet>

View File

@ -0,0 +1,11 @@
import {Component} from "@angular/core";
@Component({
selector: 'stats',
templateUrl: './stats.component.html',
styleUrls: ['./stats.component.css']
})
export class StatisticComponent {
constructor() {
}
}

View File

@ -0,0 +1,37 @@
import {Routes} from "@angular/router";
import {StatisticComponent} from "./stats.component";
import {WarDetailComponent} from "./war-detail/war-detail.component";
import {WarSubmitComponent} from "./war-submit/war-submit.component";
import {WarListComponent} from "./war-list/war-list.component";
import {StatisticOverviewComponent} from "./overview/stats-overview.component";
import {WarItemComponent} from "./war-list/war-item.component";
export const statsRoutes: Routes = [{
path: '', component: StatisticComponent,
children: [
{
path: '',
component: WarListComponent
}
]
},
{
path: 'overview',
component: StatisticOverviewComponent,
outlet: 'right'
},
{
path: 'new',
component: WarSubmitComponent,
outlet: 'right'
},
{
path: 'war/:id',
component: WarDetailComponent,
outlet: 'right'
}];
export const statsRoutingComponents = [StatisticComponent, StatisticOverviewComponent, WarListComponent,
WarSubmitComponent, WarDetailComponent, WarItemComponent];

View File

@ -1,6 +1,6 @@
<div class="overview" xmlns="http://www.w3.org/1999/html">
<div style="margin-left: 5%; min-height: 263px;">
<div style="margin-left: 2%; min-height: 263px;">
<h2>{{war.title}} - vom {{war.date | date: 'dd.MM.yyyy'}}</h2>
<h3 class="pull-left">
<h4>Endpunktestand:</h4>
@ -26,9 +26,6 @@
<div style="margin-left: 600px; margin-top:1%">
<a class="btn btn-default" style="margin: 20px" target="_blank" href="resource/logs/{{war._id}}/clean.log">Logfile
anzeigen</a>
<button *ngIf="loginService.hasPermission(3)" class="btn btn-warning" style="margin: 20px" (click)="delete()">
Schlacht löschen
</button>
<form class="form-group">
<label class="radio-inline">
<input type="radio" name="fractSelect"
@ -53,7 +50,7 @@
</div>
</div>
<div class="pull-left" style="margin-left: 5%">
<div class="pull-left" style="margin-left: 2%">
<div class="table-container scoreboard-table-container">
<table class="table table-hover" [mfData]="players" #mf="mfDataTable" [(mfSortBy)]="sortBy"
[(mfSortOrder)]="sortOrder">

View File

@ -1,8 +1,8 @@
import {Component} from "@angular/core";
import {Player, War} from "../models/model-interfaces";
import {WarService} from "../services/war-service/war.service";
import {ActivatedRoute, Router} from "@angular/router";
import {LoginService} from "../services/login-service/login-service";
import {WarService} from "../../services/war-service/war.service";
import {LoginService} from "../../services/login-service/login-service";
import {Player, War} from "../../models/model-interfaces";
@Component({
@ -24,10 +24,8 @@ export class WarDetailComponent {
playerChart: any[] = [];
constructor(private router: Router,
private route: ActivatedRoute,
private warService: WarService,
private loginService: LoginService) {
constructor(private route: ActivatedRoute,
private warService: WarService) {
Object.assign(this, this.playerChart)
}
@ -62,13 +60,4 @@ export class WarDetailComponent {
}
}
delete() {
if (confirm('Soll die Schlacht "' + this.war.title + '" wirklich gelöscht werden?')) {
this.warService.deleteWar(this.war._id)
.subscribe((res) => {
this.router.navigate(['../..'], {relativeTo: this.route});
})
}
}
}

View File

@ -0,0 +1,17 @@
<div class="fade-in list-entry" [ngClass]="{selected : selected}" (click)="select()">
<div class="row">
<div class="col-xs-9">
<span>
<a>{{war.title}}</a>
</span>
<br>
<small >vom {{war.date | date: 'dd.MM.yyyy'}}</small>
</div>
<div class="col-xs-3">
<span (click)="delete(); $event.stopPropagation()" title="Löschen" class="glyphicon glyphicon-trash trash" *ngIf="loginService.hasPermission(3)"></span>
</div>
</div>
</div>

View File

@ -0,0 +1,38 @@
import {ChangeDetectionStrategy, Component, EventEmitter} from "@angular/core";
import {War} from "../../models/model-interfaces";
import {LoginService} from "../../services/login-service/login-service";
@Component({
selector: 'pjm-war-item',
templateUrl: './war-item.component.html',
styleUrls: ['./war-item.component.css', '../../style/list-entry.css'],
changeDetection: ChangeDetectionStrategy.OnPush,
inputs: ['war', 'selected'],
outputs: ['warSelected', 'warDelete']
})
export class WarItemComponent {
selected: boolean;
war: War;
warSelected = new EventEmitter();
warDelete = new EventEmitter();
constructor(private loginService: LoginService) {
}
ngOnInit() {
}
select() {
this.warSelected.emit(this.war._id)
}
delete() {
this.warDelete.emit(this.war);
}
}

View File

@ -0,0 +1,8 @@
.search-bar {
padding-top: 20px;
padding-bottom: 20px;
}
.rank-list {
width: 100%;
}

View File

@ -0,0 +1,24 @@
<div class="war-list">
<div class="input-group search-bar" style="width:100%" *ngIf="loginService.hasPermission(3)">
<a class="pull-left btn btn-success" (click)="selectNewWar()">
Schlacht hinzufügen
</a>
</div>
<div class="fade-in list-entry" style="margin-top: 30px; margin-bottom: 30px;" [ngClass]="{selected : selectedWarId == '0'}" (click)="selectOverview()">
<div class="row">
<div class="col-xs-9">
<span style="margin:auto">
<a>Zusammenfassung</a>
</span>
</div>
</div>
</div>
<pjm-war-item *ngFor="let war of wars"
[war]="war"
(warDelete)="deleteWar(war)"
(warSelected)="selectWar($event)"
[selected]="war._id == selectedWarId">
</pjm-war-item>
</div>

View File

@ -0,0 +1,57 @@
import {Component, OnInit} from "@angular/core";
import {ActivatedRoute, Router} from "@angular/router";
import {War} from "../../models/model-interfaces";
import {WarService} from "../../services/war-service/war.service";
import {LoginService} from "../../services/login-service/login-service";
@Component({
selector: 'war-list',
templateUrl: './war-list.component.html',
styleUrls: ['./war-list.component.css', '../../style/list-entry.css']
})
export class WarListComponent implements OnInit {
selectedWarId: string | number = '0';
wars: War[] = [];
constructor(private warService: WarService,
private loginService: LoginService,
private router: Router,
private route: ActivatedRoute) {
}
ngOnInit() {
this.warService.getAllWars().subscribe((items) => {
this.wars = items;
this.router.navigate([{outlets: {'right': ['overview']}}], {relativeTo: this.route});
});
}
selectNewWar() {
this.selectedWarId = null;
this.router.navigate([{outlets: {'right': ['new']}}], {relativeTo: this.route});
}
selectWar(warId: string | number) {
this.selectedWarId = warId;
this.router.navigate([{outlets: {'right': ['war', warId]}}], {relativeTo: this.route});
}
selectOverview() {
this.selectedWarId = '0';
this.router.navigate([{outlets: {'right': ['overview']}}], {relativeTo: this.route});
}
deleteWar(war: War) {
if (confirm('Soll die Schlacht ' + war.title + ' wirklich gelöscht werden?')) {
this.warService.deleteWar(war._id)
.subscribe((res) => {
if (this.selectedWarId === war._id) {
this.selectOverview();
}
this.wars.splice(this.wars.indexOf(war), 1);
})
}
}
}

View File

@ -8,7 +8,7 @@
}
.load-arrow {
background: url(../../assets/loading.png) no-repeat;
background: url(../../../assets/loading.png) no-repeat;
display: block;
width: 120px;
height: 120px;

View File

@ -1,8 +1,8 @@
import {Component, ViewChild} from "@angular/core";
import {Player, War} from "../models/model-interfaces";
import {WarService} from "../services/war-service/war.service";
import {ActivatedRoute, Router} from "@angular/router";
import {NgForm} from "@angular/forms";
import {WarService} from "../../services/war-service/war.service";
import {War} from "../../models/model-interfaces";
@Component({

View File

@ -1,19 +0,0 @@
import {Routes} from "@angular/router";
import {WarSubmitComponent} from "./war-submit.component";
import {WarDetailComponent} from "./war-detail.component";
import {LoginGuardMT} from "../login/login.guard";
export const warRoutes: Routes = [
{
path: '',
component: WarSubmitComponent,
canActivate: [LoginGuardMT]
},
{
path: ':id',
component: WarDetailComponent,
}];
export const warsRoutingComponents = [WarSubmitComponent, WarDetailComponent];