Added nicer display for ratings in the detail view

This commit is contained in:
Simon Grimme
2022-08-19 01:21:49 +02:00
parent 1a7016d2ab
commit f652397257
5 changed files with 78 additions and 22 deletions
+5 -1
View File
@@ -51,6 +51,8 @@ import { NgModelChangeDebouncedDirective } from './directives/ng-model-change-de
import { FooterComponent } from './components/footer/footer.component'; import { FooterComponent } from './components/footer/footer.component';
import {MatExpansionModule} from "@angular/material/expansion"; import {MatExpansionModule} from "@angular/material/expansion";
import {MatSelectModule} from "@angular/material/select"; import {MatSelectModule} from "@angular/material/select";
import {MatProgressBarModule} from "@angular/material/progress-bar";
import { ProgressBarColorDirective } from './directives/progress-bar-color.directive';
@NgModule({ @NgModule({
declarations: [ declarations: [
@@ -69,6 +71,7 @@ import {MatSelectModule} from "@angular/material/select";
MappedGamesTableComponent, MappedGamesTableComponent,
UnmappedFilesTableComponent, UnmappedFilesTableComponent,
NgModelChangeDebouncedDirective, NgModelChangeDebouncedDirective,
ProgressBarColorDirective,
FooterComponent FooterComponent
], ],
imports: [ imports: [
@@ -108,7 +111,8 @@ import {MatSelectModule} from "@angular/material/select";
MatListModule, MatListModule,
MatAutocompleteModule, MatAutocompleteModule,
MatExpansionModule, MatExpansionModule,
MatSelectModule MatSelectModule,
MatProgressBarModule,
], ],
providers: [ providers: [
{ {
@@ -6,11 +6,20 @@
<img style="max-width: 264px;" src="v1/images/{{game.coverId}}" alt="Game cover"> <img style="max-width: 264px;" src="v1/images/{{game.coverId}}" alt="Game cover">
</div> </div>
<div fxFlex="40" fxLayout="column" id="game-details"> <div fxFlex="40" fxLayout="column" fxLayoutGap="16px">
<h1>{{game.title}}</h1> <h1>{{game.title}}</h1>
<h3>Rating: {{game.totalRating}}/100</h3>
<h3>Release: {{game.releaseDate | date: 'longDate'}}</h3> <h3>Release: {{game.releaseDate | date: 'longDate'}}</h3>
<p id="game-summary">{{game.summary}}</p> <p>{{game.summary}}</p>
<div *ngIf="game.criticsRating !== undefined && game.criticsRating > 0">
<h2>Critics Rating <span style="font-weight: normal; font-size: medium">({{game.criticsRating}}/100)</span></h2>
<mat-progress-bar mode="determinate" [value]="game.criticsRating" [progressBarColor]="mapRatingToColor(game.criticsRating)"></mat-progress-bar>
</div>
<div *ngIf="game.userRating !== undefined && game.userRating > 0">
<h2>User Rating <span style="font-weight: normal; font-size: medium">({{game.userRating}}/100)</span></h2>
<mat-progress-bar mode="determinate" [value]="game.userRating" [progressBarColor]="mapRatingToColor(game.userRating)"></mat-progress-bar>
</div>
</div> </div>
<div fxFlex><!-- Spacer --></div> <div fxFlex><!-- Spacer --></div>
@@ -57,7 +66,6 @@
<game-video *ngFor="let videoId of game.videoIds" [videoId]="videoId" [width]="555" [height]="312"></game-video> <game-video *ngFor="let videoId of game.videoIds" [videoId]="videoId" [width]="555" [height]="312"></game-video>
</div> </div>
</div> </div>
</div> </div>
</div> </div>
</div> </div>
@@ -1,4 +1,4 @@
import {Component, OnInit} from '@angular/core'; import {Component} from '@angular/core';
import {ActivatedRoute, Params, Router} from "@angular/router"; import {ActivatedRoute, Params, Router} from "@angular/router";
import {DetectedGameDto} from "../../models/dtos/DetectedGameDto"; import {DetectedGameDto} from "../../models/dtos/DetectedGameDto";
import {GamesService} from "../../services/games.service"; import {GamesService} from "../../services/games.service";
@@ -8,28 +8,23 @@ import {GamesService} from "../../services/games.service";
templateUrl: './game-detail-view.component.html', templateUrl: './game-detail-view.component.html',
styleUrls: ['./game-detail-view.component.scss'] styleUrls: ['./game-detail-view.component.scss']
}) })
export class GameDetailViewComponent implements OnInit { export class GameDetailViewComponent {
game!: DetectedGameDto; game!: DetectedGameDto;
constructor(private route: ActivatedRoute, constructor(private route: ActivatedRoute,
private router: Router, private router: Router,
private gamesService: GamesService) { private gamesService: GamesService) {
this.route.params.subscribe( params => { this.gamesService.getGame(this.route.snapshot.params['slug']).subscribe({
this.gamesService.getGame(params['slug']).subscribe({
next: game => this.game = game, next: game => this.game = game,
error: error => { error: error => {
if(error.status === 404) { if (error.status === 404) {
this.router.navigate(['/library']); this.router.navigate(['/library']);
} else { } else {
console.error(error); console.error(error);
} }
} }
}); });
});
}
ngOnInit(): void {
} }
public downloadGame(): void { public downloadGame(): void {
@@ -46,7 +41,7 @@ export class GameDetailViewComponent implements OnInit {
const units = ['kB', 'MB', 'GB', 'TB', 'PB', 'EB', 'ZB', 'YB']; const units = ['kB', 'MB', 'GB', 'TB', 'PB', 'EB', 'ZB', 'YB'];
const dp = 1; const dp = 1;
let u = -1; let u = -1;
const r = 10**dp; const r = 10 ** dp;
do { do {
bytes /= thresh; bytes /= thresh;
@@ -62,4 +57,11 @@ export class GameDetailViewComponent implements OnInit {
this.router.navigate(['/library'], {queryParams: params}); this.router.navigate(['/library'], {queryParams: params});
} }
mapRatingToColor(rating: number): string {
if(rating >= 75) return '#388e3c';
if(rating >= 50) return '#fbc02d';
if(rating >= 25) return '#f57c00';
return '#d32f2f';
}
} }
@@ -0,0 +1,8 @@
import { ProgressBarColorDirective } from './progress-bar-color.directive';
describe('ProgressBarColorDirective', () => {
it('should create an instance', () => {
const directive = new ProgressBarColorDirective();
expect(directive).toBeTruthy();
});
});
@@ -0,0 +1,34 @@
import { Directive, Input, OnChanges, SimpleChanges, ElementRef } from '@angular/core';
@Directive({
selector: '[progressBarColor]'
})
export class ProgressBarColorDirective implements OnChanges{
static counter = 0;
@Input() progressBarColor!: string;
styleEl:HTMLStyleElement = document.createElement('style');
//generate unique attribule which we will use to minimise the scope of our dynamic style
uniqueAttr = `app-progress-bar-color-${ProgressBarColorDirective.counter++}`;
constructor(private el: ElementRef) {
const nativeEl: HTMLElement = this.el.nativeElement;
nativeEl.setAttribute(this.uniqueAttr,'');
nativeEl.appendChild(this.styleEl);
}
ngOnChanges(changes: SimpleChanges): void{
this.updateColor();
}
updateColor(): void{
// update dynamic style with the uniqueAttr
this.styleEl.innerText = `
[${this.uniqueAttr}] .mat-progress-bar-fill::after {
background-color: ${this.progressBarColor};
}
`;
}
}