0.5.0-beta: Player vs duel bar chart implemented, add tooltips

This commit is contained in:
Tomasi - Developing 2025-01-23 13:25:47 +01:00
parent 9ba4189a0d
commit f414b60e5e
26 changed files with 364 additions and 53 deletions

View File

@ -3,7 +3,6 @@ using Application.Errors;
using Application.Interfaces;
using Asp.Versioning;
using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Http;
using Microsoft.AspNetCore.Mvc;
namespace Api.Controllers.v1
@ -36,5 +35,25 @@ namespace Api.Controllers.v1
return StatusCode(StatusCodes.Status500InternalServerError);
}
}
[HttpGet("Player/{playerId:guid}")]
public async Task<ActionResult<List<VsDuelParticipantDetailDto>>> GetPlayerVsDuelParticipants(Guid playerId, [FromQuery] int last,
CancellationToken cancellationToken)
{
try
{
var numberOfParticipationResult =
await vsDuelParticipantRepository.GetVsDuelParticipantDetailsAsync(playerId, last,
cancellationToken);
return numberOfParticipationResult.IsFailure
? BadRequest(numberOfParticipationResult.Error)
: Ok(numberOfParticipationResult.Value);
}
catch (Exception e)
{
logger.LogError(e, e.Message);
return StatusCode(StatusCodes.Status500InternalServerError);
}
}
}
}

View File

@ -0,0 +1,10 @@
namespace Application.DataTransferObjects.VsDuelParticipant;
public class VsDuelParticipantDetailDto
{
public Guid PlayerId { get; set; }
public DateTime EventDate { get; set; }
public long WeeklyPoints { get; set; }
}

View File

@ -6,4 +6,7 @@ namespace Application.Interfaces;
public interface IVsDuelParticipantRepository
{
Task<Result<VsDuelParticipantDto>> UpdateVsDuelParticipant(VsDuelParticipantDto vsDuelParticipantDto, CancellationToken cancellationToken);
Task<Result<List<VsDuelParticipantDetailDto>>> GetVsDuelParticipantDetailsAsync(Guid playerId, int last,
CancellationToken cancellationToken);
}

View File

@ -12,5 +12,8 @@ public class VsDuelParticipantProfile : Profile
.ForMember(des => des.PlayerName, opt => opt.MapFrom(src => src.Player.PlayerName));
CreateMap<VsDuelParticipantDto, VsDuelParticipant>();
CreateMap<VsDuelParticipant, VsDuelParticipantDetailDto>()
.ForMember(des => des.EventDate, opt => opt.MapFrom(src => src.VsDuel.EventDate));
}
}

View File

@ -3,6 +3,7 @@ using Application.DataTransferObjects.VsDuelParticipant;
using Application.Errors;
using Application.Interfaces;
using AutoMapper;
using AutoMapper.QueryableExtensions;
using Database;
using Microsoft.EntityFrameworkCore;
using Microsoft.Extensions.Logging;
@ -31,4 +32,17 @@ public class VsDuelParticipantRepository(ApplicationContext context, IMapper map
return Result.Failure<VsDuelParticipantDto>(GeneralErrors.DatabaseError);
}
}
public async Task<Result<List<VsDuelParticipantDetailDto>>> GetVsDuelParticipantDetailsAsync(Guid playerId, int last, CancellationToken cancellationToken)
{
var vsDuelPlayersParticipants = await context.VsDuelParticipants
.ProjectTo<VsDuelParticipantDetailDto>(mapper.ConfigurationProvider)
.AsNoTracking()
.OrderByDescending(e => e.EventDate)
.Where(e => e.PlayerId == playerId)
.Take(last)
.ToListAsync(cancellationToken);
return Result.Success(vsDuelPlayersParticipants);
}
}

View File

@ -13,6 +13,11 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Application", "Application\
EndProject
Project("{54A90642-561A-4BB1-A94E-469ADEE60C69}") = "Ui", "Ui\Ui.esproj", "{77168004-AF1E-4F51-A096-E8E8BF18A37A}"
EndProject
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Projektmappenelemente", "Projektmappenelemente", "{E8BE2EF5-0D8D-4D68-9979-0680938F26DF}"
ProjectSection(SolutionItems) = preProject
README.md = README.md
EndProjectSection
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU

View File

@ -1 +1,96 @@
# PlayerManagement
# PlayerManagement
## Changelog
All notable changes to this project are documented here.
This project is currently in the **Beta Phase**.
---
### **[0.5.0-beta]** - *2025-01-21*
#### ✨ Added
- **Player VS Duel**: In the player detail view, the VS points can now be viewed as a bar chart.
#### 🛠️ Fixed
- *(N/A)*
---
### **[0.4.1-beta]** - *2025-01-21*
#### ✨ Added
- **Excel Import**: Players can now be imported via Excel.
#### 🛠️ Fixed
- **Week Pipe Logic**: Corrected calculation logic for weekly processing.
---
### **[0.4.0-beta]** - *2025-01-20*
#### ✨ Added
- **Player Dismissal Page**: A new GUI page was added for dismissing players.
#### 🛠️ Fixed
- *(N/A)*
---
### **[0.3.6-beta]** - *2025-01-16*
#### ✨ Added
- **Player Dismissal Function**: Core dismissal functionality implemented.
#### 🛠️ Fixed
- *(N/A)*
---
### **[0.3.5-beta]** - *2025-01-09*
#### ✨ Added
- *(N/A)*
#### 🛠️ Fixed
- **MVP Formula**: Corrected MVP calculation formula.
---
### **[0.3.4-beta]** - *2025-01-07*
#### ✨ Added
- **Alliance MVP Calculation**: Implemented MVP calculation for alliances with API endpoint support.
#### 🛠️ Fixed
- *(N/A)*
---
### **[0.3.3-beta]** - *2024-12-17*
#### ✨ Added
- **Custom Event**: Introduced custom event functionality.
#### 🛠️ Fixed
- *(N/A)*
---
### **[0.3.2-beta]** - *2024-12-03*
#### ✨ Added
- **Event Progress**: "In Progress" status added to events.
- **League Details in VS Duel**: Added league tiers (e.g., Silver, Gold, Diamond).
#### 🛠️ Fixed
- *(N/A)*
---
### **[0.3.1-beta]** - *2024-11-28*
#### ✨ Added
- **Zombie Siege Event**: Introduced a new Zombie Siege event.
#### 🛠️ Fixed
- *(N/A)*
---
### **[0.3.0-beta]** - *2024-11-26*
#### ✨ Added
- **Initial Beta Release**: Core features introduced in the first beta release.
#### 🛠️ Fixed
- *(N/A in the initial release)*

36
Ui/package-lock.json generated
View File

@ -20,6 +20,7 @@
"@ng-bootstrap/ng-bootstrap": "^17.0.1",
"@popperjs/core": "^2.11.8",
"@sweetalert2/theme-dark": "^5.0.18",
"ag-charts-angular": "^11.0.4",
"bootstrap": "^5.3.2",
"bootstrap-icons": "^1.11.3",
"bootswatch": "^5.3.3",
@ -5226,6 +5227,41 @@
"node": ">=8.9.0"
}
},
"node_modules/ag-charts-angular": {
"version": "11.0.4",
"resolved": "https://registry.npmjs.org/ag-charts-angular/-/ag-charts-angular-11.0.4.tgz",
"integrity": "sha512-1D9xEky6RcwJ49SLGScrVyJNOIy+wH32CaEY4JTdS36QqgFcOVwm5QTiMf/zTa+Qsbz4HfRVBkYpBQuMR0s2Cw==",
"dependencies": {
"tslib": "^2.3.0"
},
"peerDependencies": {
"@angular/common": "^17.0.0 || ^18.0.0 || ^19.0.0",
"@angular/core": "^17.0.0 || ^18.0.0 || ^19.0.0",
"ag-charts-community": "11.0.4"
}
},
"node_modules/ag-charts-community": {
"version": "11.0.4",
"resolved": "https://registry.npmjs.org/ag-charts-community/-/ag-charts-community-11.0.4.tgz",
"integrity": "sha512-TFShWfZaA1yJ/hb3jwtNAqBG2Qy9VvoQ9mWLr29ilT6+2R2e30RSk2oH7FAQ2l5nS1367dRf137Td9tUTTuVLg==",
"peer": true,
"dependencies": {
"ag-charts-locale": "11.0.4",
"ag-charts-types": "11.0.4"
}
},
"node_modules/ag-charts-locale": {
"version": "11.0.4",
"resolved": "https://registry.npmjs.org/ag-charts-locale/-/ag-charts-locale-11.0.4.tgz",
"integrity": "sha512-xCQA8CtcUyqU4qYg7u9oUQ+SghIsWAQvY60Bu0ghJJ/bDeW8+ptEU0ogBapuDqfb9B9kqWKgASxbX6diqb+HVQ==",
"peer": true
},
"node_modules/ag-charts-types": {
"version": "11.0.4",
"resolved": "https://registry.npmjs.org/ag-charts-types/-/ag-charts-types-11.0.4.tgz",
"integrity": "sha512-K/Mi7FXvSCoABLSrqQ70k1QrIL5R6RNCt2NAppOxMEir+DVFPqKZtghruobc2MGVUUKkT9MCn6Dun+fL6yZjfA==",
"peer": true
},
"node_modules/agent-base": {
"version": "7.1.1",
"resolved": "https://registry.npmjs.org/agent-base/-/agent-base-7.1.1.tgz",

View File

@ -22,6 +22,7 @@
"@ng-bootstrap/ng-bootstrap": "^17.0.1",
"@popperjs/core": "^2.11.8",
"@sweetalert2/theme-dark": "^5.0.18",
"ag-charts-angular": "^11.0.4",
"bootstrap": "^5.3.2",
"bootstrap-icons": "^1.11.3",
"bootswatch": "^5.3.3",

View File

@ -27,7 +27,6 @@ import {jwtInterceptor} from "./interceptors/jwt.interceptor";
import { PlayerNoteModalComponent } from './modals/player-note-modal/player-note-modal.component';
import { PlayerAdmonitionModalComponent } from './modals/player-admonition-modal/player-admonition-modal.component';
import { PlayerInfoMarshalGuardComponent } from './pages/player-information/player-info-marshal-guard/player-info-marshal-guard.component';
import { PlayerInfoVsDuelComponent } from './pages/player-information/player-info-vs-duel/player-info-vs-duel.component';
import { WeekPipe } from './helpers/week.pipe';
import { PlayerInfoDesertStormComponent } from './pages/player-information/player-info-desert-storm/player-info-desert-storm.component';
import { PlayerInfoCustomEventComponent } from './pages/player-information/player-info-custom-event/player-info-custom-event.component';
@ -55,6 +54,8 @@ import { CustomEventDetailComponent } from './pages/custom-event/custom-event-de
import { DismissPlayerComponent } from './pages/dismiss-player/dismiss-player.component';
import { PlayerDismissInformationModalComponent } from './modals/player-dismiss-information-modal/player-dismiss-information-modal.component';
import { PlayerExcelImportModalComponent } from './modals/player-excel-import-modal/player-excel-import-modal.component';
import {AgCharts} from "ag-charts-angular";
import {PlayerInfoVsDuelComponent} from "./pages/player-information/player-info-vs-duel/player-info-vs-duel.component";
@NgModule({
declarations: [
@ -73,10 +74,10 @@ import { PlayerExcelImportModalComponent } from './modals/player-excel-import-mo
PlayerNoteModalComponent,
PlayerAdmonitionModalComponent,
PlayerInfoMarshalGuardComponent,
PlayerInfoVsDuelComponent,
WeekPipe,
PlayerInfoDesertStormComponent,
PlayerInfoCustomEventComponent,
PlayerInfoVsDuelComponent,
VsDuelCreateModalComponent,
VsDuelDetailComponent,
VsDuelEditComponent,
@ -102,25 +103,26 @@ import { PlayerExcelImportModalComponent } from './modals/player-excel-import-mo
PlayerDismissInformationModalComponent,
PlayerExcelImportModalComponent
],
imports: [
BrowserModule,
AppRoutingModule,
BrowserAnimationsModule,
NgbModule,
FormsModule,
NgxPaginationModule,
ReactiveFormsModule,
NgxSpinnerModule,
NgbRatingModule,
ToastrModule.forRoot({
positionClass: 'toast-bottom-right',
}),
JwtModule.forRoot({
config: {
tokenGetter: () => localStorage.getItem(''),
}
})
],
imports: [
BrowserModule,
AppRoutingModule,
BrowserAnimationsModule,
NgbModule,
FormsModule,
NgxPaginationModule,
ReactiveFormsModule,
NgxSpinnerModule,
NgbRatingModule,
ToastrModule.forRoot({
positionClass: 'toast-bottom-right',
}),
JwtModule.forRoot({
config: {
tokenGetter: () => localStorage.getItem(''),
}
}),
AgCharts
],
providers: [
provideHttpClient(withInterceptors([spinnerInterceptor, jwtInterceptor]))
],

View File

@ -5,3 +5,9 @@ export interface VsDuelParticipantModel {
weeklyPoints: number;
playerName: string;
}
export interface VsDuelParticipantDetailModel {
playerId: string;
eventDate: Date;
weeklyPoints: number;
}

View File

@ -6,7 +6,7 @@
<a class="navbar-brand" routerLink="/">{{loggedInUser.allianceName}}</a>
<!-- Displaying the application version -->
<span class="version">v.{{version}}</span>
<span ngbTooltip="Changelog" placement="auto" (click)="onVersion()" class="version">v.{{version}}</span>
<!-- Toggle button for collapsed navigation on smaller screens -->
<button (click)="isShown = !isShown" aria-controls="navbar" aria-expanded="false" aria-label="Toggle navigation"

View File

@ -41,4 +41,8 @@ export class NavigationComponent implements OnInit, OnDestroy {
this._authStateChange$.unsubscribe();
}
}
onVersion() {
window.open('https://github.com/TomasiDeveloping/PlayerManagement', '_blank');
}
}

View File

@ -98,8 +98,8 @@
<td>{{user.role}}</td>
<td>
<div class="d-flex justify-content-around">
<i (click)="onEditUser(user)" class="bi custom-edit-icon bi-pencil-fill"></i>
<i (click)="onDeleteUser(user)" class="bi custom-delete-icon bi-trash3"></i>
<i ngbTooltip="Edit" placement="auto" (click)="onEditUser(user)" class="bi custom-edit-icon bi-pencil-fill"></i>
<i ngbTooltip="Delete" placement="auto" (click)="onDeleteUser(user)" class="bi custom-delete-icon bi-trash3"></i>
</div>
</td>
</tr>

View File

@ -135,9 +135,9 @@
<td>{{customEvent.createdBy}}</td>
<td>
<div class="d-flex gap-3 justify-content-around">
<i (click)="onGoToCustomEventDetail(customEvent)" class="bi custom-info-icon bi-info-circle-fill"></i>
<i (click)="onEditCustomEvent(customEvent)" class="bi custom-edit-icon bi-pencil-fill"></i>
<i (click)="onDeleteCustomEvent(customEvent)" class="bi custom-delete-icon bi-trash3"></i>
<i ngbTooltip="Show details" placement="auto" (click)="onGoToCustomEventDetail(customEvent)" class="bi custom-info-icon bi-info-circle-fill"></i>
<i ngbTooltip="Edit" placement="auto" (click)="onEditCustomEvent(customEvent)" class="bi custom-edit-icon bi-pencil-fill"></i>
<i ngbTooltip="Delete" placement="auto" (click)="onDeleteCustomEvent(customEvent)" class="bi custom-delete-icon bi-trash3"></i>
</div>
</td>
</tr>

View File

@ -143,9 +143,9 @@
</td>
<td>
<div class="d-flex gap-3 justify-content-around">
<i (click)="onDesertStormDetail(desertStorm)" class="bi custom-info-icon bi-info-circle-fill"></i>
<i (click)="onEditDesertStorm(desertStorm)" class="bi custom-edit-icon bi-pencil-fill"></i>
<i (click)="onDeleteDesertStorm(desertStorm)" class="bi custom-delete-icon bi-trash3"></i>
<i ngbTooltip="Show details" placement="auto" (click)="onDesertStormDetail(desertStorm)" class="bi custom-info-icon bi-info-circle-fill"></i>
<i ngbTooltip="Edit" placement="auto" (click)="onEditDesertStorm(desertStorm)" class="bi custom-edit-icon bi-pencil-fill"></i>
<i ngbTooltip="Delete" placement="auto" (click)="onDeleteDesertStorm(desertStorm)" class="bi custom-delete-icon bi-trash3"></i>
</div>
</td>
</tr>

View File

@ -22,9 +22,9 @@
<td>{{player.dismissalReason}}</td>
<td>
<div class="d-flex gap-3 justify-content-around">
<i (click)="onPlayerInformation(player)" class="bi custom-info-icon bi-info-circle-fill"></i>
<i (click)="onReactivePlayer(player)" class="bi custom-edit-icon bi-bootstrap-reboot"></i>
<i (click)="onDeletePlayer(player)" class="bi custom-delete-icon bi bi-trash3"></i>
<i ngbTooltip="Show information" placement="auto" (click)="onPlayerInformation(player)" class="bi custom-info-icon bi-info-circle-fill"></i>
<i ngbTooltip="Rejoining" placement="auto" (click)="onReactivePlayer(player)" class="bi custom-edit-icon bi-bootstrap-reboot"></i>
<i ngbTooltip="Delete" placement="auto" (click)="onDeletePlayer(player)" class="bi custom-delete-icon bi bi-trash3"></i>
</div>
</td>
</tr>

View File

@ -110,9 +110,9 @@
<td>{{marshalGuard.createdBy}}</td>
<td>
<div class="d-flex gap-3 justify-content-around">
<i (click)="onGoToMarshalGuardDetail(marshalGuard)" class="bi custom-info-icon bi-info-circle-fill"></i>
<i (click)="onEditMarshalGuard(marshalGuard)" class="bi custom-edit-icon bi-pencil-fill"></i>
<i (click)="onDeleteMarshalGuard(marshalGuard)" class="bi custom-delete-icon bi-trash3"></i>
<i ngbTooltip="Show details" placement="auto" (click)="onGoToMarshalGuardDetail(marshalGuard)" class="bi custom-info-icon bi-info-circle-fill"></i>
<i ngbTooltip="Edit" placement="auto" (click)="onEditMarshalGuard(marshalGuard)" class="bi custom-edit-icon bi-pencil-fill"></i>
<i ngbTooltip="Delete" placement="auto" (click)="onDeleteMarshalGuard(marshalGuard)" class="bi custom-delete-icon bi-trash3"></i>
</div>
</td>
</tr>

View File

@ -0,0 +1,3 @@
ag-charts {
display: block;
}

View File

@ -1 +1,21 @@
<app-under-development></app-under-development>
<div>
<form class="d-flex gap-2 align-items-center justify-content-center mb-3">
<div>
<label for="inputField" class="col-form-label">Last:</label>
</div>
<div>
<input [ngModelOptions]="{standalone: true}" type="number" id="inputField" class="form-control" placeholder="Input"
[(ngModel)]="numberOfLoadVsDuels">
</div>
<div>
<button (click)="onReloadVsDuels()" type="submit"
class="btn btn-primary">{{ vsDuelsLoaded ? 'Reload' : 'load' }}
</button>
</div>
</form>
@if (vsDuelsLoaded) {
<ag-charts [options]="options"></ag-charts>
}
</div>

View File

@ -1,10 +1,92 @@
import {Component} from '@angular/core';
import {Component, inject, Input} from '@angular/core';
import { AgChartOptions } from "ag-charts-community";
import {DatePipe} from "@angular/common";
import {VsDuelParticipantService} from "../../../services/vs-duel-participant.service";
import {ToastrService} from "ngx-toastr";
@Component({
selector: 'app-player-info-vs-duel',
templateUrl: './player-info-vs-duel.component.html',
styleUrl: './player-info-vs-duel.component.css'
styleUrl: './player-info-vs-duel.component.css',
providers: [DatePipe]
})
export class PlayerInfoVsDuelComponent {
@Input({required: true}) playerId!: string;
private readonly _vsDuelParticipantsService: VsDuelParticipantService = inject(VsDuelParticipantService);
private readonly _datePipe: DatePipe = inject(DatePipe);
private readonly _toastr: ToastrService = inject(ToastrService);
numberOfLoadVsDuels: number = 10;
vsDuelsLoaded: boolean = false;
options: AgChartOptions = {
title: {
text: 'Weekly Points'
},
data: [],
series: [
{
type: 'bar',
xKey: 'date',
xName: 'Date',
yKey: 'points',
yName: 'Weekly Points',
stacked: false,
fill: 'blue'
}
],
axes: [
{
type: 'number',
position: 'left',
label: {
formatter: (params: any) => {
return params.value.toLocaleString('en-US')
}
}
},
{
type: 'category',
position: 'bottom',
}
]
}
getData(take: number) {
const chartData: {date: string, points: number}[] = [];
this._vsDuelParticipantsService.getVsDuelParticipantsDetail(this.playerId, take).subscribe({
next: ((response) => {
if (response) {
this.vsDuelsLoaded = true;
if (response.length < take) {
this._toastr.info('Fewer vs duels were held than wanted to be loaded');
this.numberOfLoadVsDuels = response.length;
}
response.forEach(player => {
const data: {date: string, points: number} = {
date: this._datePipe.transform(player.eventDate, 'dd.MM.yyyy')!,
points: player.weeklyPoints
};
chartData.push(data)
})
this.options = {
...this.options,
data: chartData.reverse()
}
}
}),
error: error => {
console.log(error);
}
})
}
onReloadVsDuels() {
this.getData(this.numberOfLoadVsDuels);
}
}

View File

@ -59,7 +59,7 @@
</h2>
<div ngbAccordionCollapse>
<div ngbAccordionBody>
<app-player-info-vs-duel></app-player-info-vs-duel>
<app-player-info-vs-duel [playerId]="playerId"></app-player-info-vs-duel>
</div>
</div>
</div>

View File

@ -58,7 +58,7 @@
{{player.playerName}}
</div>
<div class="col">
<i (click)="onGoToPlayerInformation(player)" class="bi custom-info-icon bi-info-circle-fill"></i>
<i ngbTooltip="Show information" placement="auto" (click)="onGoToPlayerInformation(player)" class="bi custom-info-icon bi-info-circle-fill"></i>
</div>
</div>
</td>
@ -66,8 +66,8 @@
<td>{{player.rankName}}</td>
<td>
<div class="d-flex gap-3 justify-content-around">
<i (click)="onEditPlayer(player)" class="bi custom-edit-icon bi-pencil-fill"></i>
<i (click)="onDismissPlayer(player)" class="bi custom-delete-icon bi-person-dash"></i>
<i ngbTooltip="Edit" placement="auto" (click)="onEditPlayer(player)" class="bi custom-edit-icon bi-pencil-fill"></i>
<i ngbTooltip="Dismiss" placement="auto" (click)="onDismissPlayer(player)" class="bi custom-delete-icon bi-person-dash"></i>
</div>
</td>
</tr>

View File

@ -64,9 +64,9 @@
}</td>
<td>
<div class="d-flex gap-3 justify-content-around">
<i (click)="onGoToVsDuelInformation(vsDuel)" class="bi custom-info-icon bi-info-circle-fill"></i>
<i (click)="onEditVsDuel(vsDuel)" class="bi custom-edit-icon bi-pencil-fill"></i>
<i (click)="onDeleteVsDuel(vsDuel)" class="bi custom-delete-icon bi-trash3"></i>
<i ngbTooltip="Show details" placement="auto" (click)="onGoToVsDuelInformation(vsDuel)" class="bi custom-info-icon bi-info-circle-fill"></i>
<i ngbTooltip="Edit" placement="auto" (click)="onEditVsDuel(vsDuel)" class="bi custom-edit-icon bi-pencil-fill"></i>
<i ngbTooltip="Delete" placement="auto" (click)="onDeleteVsDuel(vsDuel)" class="bi custom-delete-icon bi-trash3"></i>
</div>
</td>
</tr>

View File

@ -92,9 +92,9 @@
<td>{{zombieSiege.createdBy}}</td>
<td>
<div class="d-flex gap-3 justify-content-around">
<i (click)="onGoToZombieSiegeDetail(zombieSiege)" class="bi custom-info-icon bi-info-circle-fill"></i>
<i (click)="onEditZombieSiege(zombieSiege)" class="bi custom-edit-icon bi-pencil-fill"></i>
<i (click)="onDeleteZombieSiege(zombieSiege)" class="bi custom-delete-icon bi-trash3"></i>
<i ngbTooltip="Show details" placement="auto" (click)="onGoToZombieSiegeDetail(zombieSiege)" class="bi custom-info-icon bi-info-circle-fill"></i>
<i ngbTooltip="Edit" placement="auto" (click)="onEditZombieSiege(zombieSiege)" class="bi custom-edit-icon bi-pencil-fill"></i>
<i ngbTooltip="Delete" placement="auto" (click)="onDeleteZombieSiege(zombieSiege)" class="bi custom-delete-icon bi-trash3"></i>
</div>
</td>
</tr>

View File

@ -1,8 +1,9 @@
import {inject, Injectable} from '@angular/core';
import {environment} from "../../environments/environment";
import {HttpClient} from "@angular/common/http";
import {VsDuelParticipantModel} from "../models/vsDuelParticipant.model";
import {HttpClient, HttpParams} from "@angular/common/http";
import {VsDuelParticipantDetailModel, VsDuelParticipantModel} from "../models/vsDuelParticipant.model";
import {Observable} from "rxjs";
import {MarshalGuardParticipantModel} from "../models/marshalGuardParticipant.model";
@Injectable({
providedIn: 'root'
@ -12,6 +13,13 @@ export class VsDuelParticipantService {
private readonly _serviceUrl = environment.apiBaseUrl + 'VsDuelParticipants/';
private readonly _httpClient: HttpClient = inject(HttpClient);
getVsDuelParticipantsDetail(playerId: string, last: number): Observable<VsDuelParticipantDetailModel[]> {
let params = new HttpParams();
params = params.append('last', last);
return this._httpClient.get<VsDuelParticipantDetailModel[]>(this._serviceUrl + 'Player/' + playerId, {params: params});
}
updateVsDuelParticipant(vsDuelParticipantId: string, vsDuelParticipant: VsDuelParticipantModel): Observable<VsDuelParticipantModel> {
return this._httpClient.put<VsDuelParticipantModel>(this._serviceUrl + vsDuelParticipantId, vsDuelParticipant);
}