Added match history UI card & array reverse pipe
This commit is contained in:
@@ -12,5 +12,5 @@
|
|||||||
<ng-template #matchResults>
|
<ng-template #matchResults>
|
||||||
<app-match-results></app-match-results>
|
<app-match-results></app-match-results>
|
||||||
</ng-template>
|
</ng-template>
|
||||||
<!-- game-history component -->
|
<app-match-history *ngIf="hasHatchHistory$ | async"></app-match-history>
|
||||||
</div>
|
</div>
|
||||||
@@ -9,21 +9,25 @@ import { EffectsModule } from '@ngrx/effects';
|
|||||||
import { MatButtonModule } from '@angular/material/button';
|
import { MatButtonModule } from '@angular/material/button';
|
||||||
import { MatCardModule } from '@angular/material/card';
|
import { MatCardModule } from '@angular/material/card';
|
||||||
import { MatIconModule } from '@angular/material/icon';
|
import { MatIconModule } from '@angular/material/icon';
|
||||||
|
import { MatListModule } from '@angular/material/list';
|
||||||
import { MatRadioModule } from '@angular/material/radio';
|
import { MatRadioModule } from '@angular/material/radio';
|
||||||
import { MatToolbarModule } from '@angular/material/toolbar';
|
import { MatToolbarModule } from '@angular/material/toolbar';
|
||||||
|
|
||||||
import { AppComponent } from './app.component';
|
import { AppComponent } from './app.component';
|
||||||
import { GameStoreModule } from './store';
|
import { GameStoreModule } from './store';
|
||||||
import { DirectivesModule } from './directives/directives.module';
|
import { DirectivesModule } from './directives/directives.module';
|
||||||
|
import { PipesModule } from './pipes/pipes.module';
|
||||||
|
|
||||||
import { GameCardComponent } from './game-card/game-card.component';
|
import { GameCardComponent } from './game-card/game-card.component';
|
||||||
import { MatchResultsComponent } from './match-results/match-results.component';
|
import { MatchResultsComponent } from './match-results/match-results.component';
|
||||||
import { ScoreCardComponent } from './score-card/score-card.component';
|
import { ScoreCardComponent } from './score-card/score-card.component';
|
||||||
|
import { MatchHistoryComponent } from './match-history/match-history.component';
|
||||||
|
|
||||||
const materialModules = [
|
const materialModules = [
|
||||||
MatButtonModule,
|
MatButtonModule,
|
||||||
MatCardModule,
|
MatCardModule,
|
||||||
MatIconModule,
|
MatIconModule,
|
||||||
|
MatListModule,
|
||||||
MatRadioModule,
|
MatRadioModule,
|
||||||
MatToolbarModule
|
MatToolbarModule
|
||||||
];
|
];
|
||||||
@@ -33,7 +37,8 @@ const materialModules = [
|
|||||||
AppComponent,
|
AppComponent,
|
||||||
GameCardComponent,
|
GameCardComponent,
|
||||||
MatchResultsComponent,
|
MatchResultsComponent,
|
||||||
ScoreCardComponent
|
ScoreCardComponent,
|
||||||
|
MatchHistoryComponent
|
||||||
],
|
],
|
||||||
imports: [
|
imports: [
|
||||||
BrowserModule,
|
BrowserModule,
|
||||||
@@ -44,6 +49,7 @@ const materialModules = [
|
|||||||
StoreModule.forRoot({}, {}),
|
StoreModule.forRoot({}, {}),
|
||||||
EffectsModule.forRoot([]),
|
EffectsModule.forRoot([]),
|
||||||
DirectivesModule,
|
DirectivesModule,
|
||||||
|
PipesModule,
|
||||||
GameStoreModule
|
GameStoreModule
|
||||||
],
|
],
|
||||||
providers: [],
|
providers: [],
|
||||||
|
|||||||
40
src/app/match-history/match-history.component.css
Normal file
40
src/app/match-history/match-history.component.css
Normal file
@@ -0,0 +1,40 @@
|
|||||||
|
:host {
|
||||||
|
display: block;
|
||||||
|
margin-top: 1rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
.match-history-card {
|
||||||
|
width: var(--card-width);
|
||||||
|
}
|
||||||
|
|
||||||
|
.match-list-item {
|
||||||
|
display: flex;
|
||||||
|
flex-direction: row;
|
||||||
|
justify-content: space-between;
|
||||||
|
width: 100%;
|
||||||
|
}
|
||||||
|
|
||||||
|
.match-visual {
|
||||||
|
display: flex;
|
||||||
|
flex-direction: row;
|
||||||
|
align-items: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
.match-visual > * {
|
||||||
|
margin-right: 1rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
.match-visual img {
|
||||||
|
width: 25px;
|
||||||
|
height: auto;
|
||||||
|
}
|
||||||
|
|
||||||
|
.result {
|
||||||
|
font-size: 1.2rem;
|
||||||
|
font-weight: 500;
|
||||||
|
}
|
||||||
|
|
||||||
|
.match-visual .vs {
|
||||||
|
font-size: 1.2rem;
|
||||||
|
font-weight: 500;
|
||||||
|
}
|
||||||
17
src/app/match-history/match-history.component.html
Normal file
17
src/app/match-history/match-history.component.html
Normal file
@@ -0,0 +1,17 @@
|
|||||||
|
<mat-card class="match-history-card">
|
||||||
|
<mat-card-title>Match History</mat-card-title>
|
||||||
|
<mat-card-content>
|
||||||
|
<mat-list *ngLet="matchHistory$ | async; let matchHistory;" class="match-history-list">
|
||||||
|
<mat-list-item *ngFor="let item of matchHistory | reverseArray">
|
||||||
|
<div class="match-list-item">
|
||||||
|
<div class="match-visual">
|
||||||
|
<img src="./assets/{{ item.playerChoice }}-50.png" [alt]="item.playerChoice">
|
||||||
|
<span class="vs">vs</span>
|
||||||
|
<img src="./assets/{{ item.computerChoice }}-50.png" [alt]="item.computerChoice">
|
||||||
|
</div>
|
||||||
|
<span class="result">{{ item.result }}</span>
|
||||||
|
</div>
|
||||||
|
</mat-list-item>
|
||||||
|
</mat-list>
|
||||||
|
</mat-card-content>
|
||||||
|
</mat-card>
|
||||||
17
src/app/match-history/match-history.component.ts
Normal file
17
src/app/match-history/match-history.component.ts
Normal file
@@ -0,0 +1,17 @@
|
|||||||
|
import { Component } from '@angular/core';
|
||||||
|
|
||||||
|
import { GameFacade } from '../store/game';
|
||||||
|
|
||||||
|
@Component({
|
||||||
|
selector: 'app-match-history',
|
||||||
|
templateUrl: './match-history.component.html',
|
||||||
|
styleUrls: ['./match-history.component.css']
|
||||||
|
})
|
||||||
|
export class MatchHistoryComponent {
|
||||||
|
matchHistory$ = this.gameFacade.matchHistory$;
|
||||||
|
|
||||||
|
constructor(
|
||||||
|
private readonly gameFacade: GameFacade
|
||||||
|
) { }
|
||||||
|
|
||||||
|
}
|
||||||
@@ -1,6 +1,5 @@
|
|||||||
<mat-card *ngLet="results$ | async; let results;" class="match-results">
|
<mat-card *ngLet="results$ | async; let results;" class="match-results">
|
||||||
<mat-card-title>Match Results</mat-card-title>
|
<mat-card-title>Match Results</mat-card-title>
|
||||||
<!-- {"playerChoice":"rock","computerChoice":"scissors","result":"win"} -->
|
|
||||||
<mat-card-content>
|
<mat-card-content>
|
||||||
<div class="match-results-text">You {{ results.result }}!</div>
|
<div class="match-results-text">You {{ results.result }}!</div>
|
||||||
<div class="match-visual">
|
<div class="match-visual">
|
||||||
|
|||||||
20
src/app/pipes/pipes.module.ts
Normal file
20
src/app/pipes/pipes.module.ts
Normal file
@@ -0,0 +1,20 @@
|
|||||||
|
import { NgModule } from '@angular/core';
|
||||||
|
|
||||||
|
import { ReverseArrayPipe } from './reverse-array.pipe';
|
||||||
|
|
||||||
|
const exportedPipes = [
|
||||||
|
ReverseArrayPipe
|
||||||
|
];
|
||||||
|
|
||||||
|
@NgModule({
|
||||||
|
declarations: [
|
||||||
|
...exportedPipes,
|
||||||
|
],
|
||||||
|
providers: [
|
||||||
|
...exportedPipes
|
||||||
|
],
|
||||||
|
exports: [
|
||||||
|
...exportedPipes
|
||||||
|
]
|
||||||
|
})
|
||||||
|
export class PipesModule { }
|
||||||
12
src/app/pipes/reverse-array.pipe.ts
Normal file
12
src/app/pipes/reverse-array.pipe.ts
Normal file
@@ -0,0 +1,12 @@
|
|||||||
|
import { Pipe, PipeTransform } from '@angular/core';
|
||||||
|
|
||||||
|
@Pipe({
|
||||||
|
name: 'reverseArray'
|
||||||
|
})
|
||||||
|
export class ReverseArrayPipe implements PipeTransform {
|
||||||
|
|
||||||
|
transform(input: any[]): any[] {
|
||||||
|
return Array.isArray(input) ? input.slice().reverse() : input
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
@@ -46,7 +46,7 @@ export const reducer = createReducer(
|
|||||||
);
|
);
|
||||||
|
|
||||||
export const getHasMatchHistory = (state: State) => state.gameHistory.length > 0;
|
export const getHasMatchHistory = (state: State) => state.gameHistory.length > 0;
|
||||||
export const getMatchHistory = (state: State) => state.gameHistory;
|
export const getMatchHistory = (state: State) => state.gameHistory.filter(h => h.result !== 'error');
|
||||||
export const getGameStatus = (state: State) => state.gameStatus;
|
export const getGameStatus = (state: State) => state.gameStatus;
|
||||||
export const getRecentMatchHistory = (state: State) => state.gameHistory.slice(-1).pop();
|
export const getRecentMatchHistory = (state: State) => state.gameHistory.slice(-1).pop();
|
||||||
export const getPlayerScore = (state: State) => state.gameHistory.reduce((acc, match) => acc += Number(match.result === 'win'), 0);
|
export const getPlayerScore = (state: State) => state.gameHistory.reduce((acc, match) => acc += Number(match.result === 'win'), 0);
|
||||||
|
|||||||
Reference in New Issue
Block a user