1
0
mirror of synced 2024-12-18 09:25:56 +01:00
TaikoLocalServer/TaikoWebUI/Pages/DaniDojo.razor

483 lines
41 KiB
Plaintext

@using System.ComponentModel.DataAnnotations
@using Blazored.LocalStorage
@inject IGameDataService GameDataService
@inject HttpClient Client
@inject AuthService AuthService
@inject NavigationManager NavigationManager
@inject ILocalStorageService LocalStorage
@inject BreadcrumbsStateContainer BreadcrumbsStateContainer
@page "/Users/{baid:int}/DaniDojo"
@if (AuthService.LoginRequired && (!AuthService.IsLoggedIn || (AuthService.GetLoggedInBaid() != Baid && !AuthService.IsAdmin)))
{
if (!AuthService.IsLoggedIn)
{
NavigationManager.NavigateTo("/Login");
}
else
{
NavigationManager.NavigateTo("/");
}
}
else
{
<MudGrid Class="my-4 pb-10">
<MudItem xs="12">
<MudPaper Elevation="0" Outlined="true">
<MudTabs ActivePanelIndex="0" Rounded="true" Border="true" MinimumTabWidth="100px" PanelClass="pa-8">
@foreach (var danId in danMap.Keys)
{
var danData = danMap[danId];
<MudTabPanel Text="@GetDanTitle(danData.Title)" Icon="@GetDanResultIcon(danId)">
<MudText Typo="Typo.h5" Class="mb-4">@Localizer["Details"]</MudText>
<MudGrid Class="d-flex">
<MudItem xs="12" sm="12" md="4" Class="pb-1">
<MudCard Outlined="true" Style="height:100%;">
<MudCardHeader Class="pb-0">
<CardHeaderContent>
<MudText Typo="Typo.h6">@Localizer["Result"]</MudText>
</CardHeaderContent>
</MudCardHeader>
<MudCardContent Class="d-flex py-10" Style="justify-content:center;">
<MudStack Justify="Justify.Center" AlignItems="AlignItems.Center" Spacing="6">
@{
var danResultState = GetDanResultState(danId);
var danClearStateString = GetDanClearStateString(danResultState);
}
<img src=@($"/images/dani_{danResultState.ToString()}.webp") style="max-width:150px; width:100%;" alt="danResultState.ToString()"/>
<MudText Typo="Typo.body1">@danClearStateString</MudText>
</MudStack>
</MudCardContent>
</MudCard>
</MudItem>
<MudItem xs="12" sm="12" md="8" Class="pb-1">
<MudStack>
<MudCard Outlined="true">
<MudCardHeader Class="pb-0">
<CardHeaderContent>
<MudText Typo="Typo.h6">@Localizer["Score"]</MudText>
</CardHeaderContent>
</MudCardHeader>
<MudCardContent Class="d-flex py-10" Style="justify-content:center">
@{
var totalScore = GetTotalScore(danId);
}
<MudStack Row="true" Spacing="4" Justify="Justify.SpaceEvenly" Style="width:100%">
<MudText Typo="Typo.h4">@totalScore</MudText>
</MudStack>
</MudCardContent>
</MudCard>
<MudCard Outlined="true">
<MudCardHeader Class="pb-0">
<CardHeaderContent>
<MudText Typo="Typo.h6">@Localizer["Totals"]</MudText>
</CardHeaderContent>
</MudCardHeader>
<MudCardContent Class="d-flex py-10" Style="justify-content:center">
@{
var totalGoods = GetTotalGoodHits(danId);
var totalOks = GetTotalOkHits(danId);
var totalBads = GetTotalBadHits(danId);
var totalDrumroll = GetTotalDrumrollHits(danId);
var totalMaxCombo = GetTotalMaxCombo(danId);
var totalHits = GetTotalHits(danId);
}
<MudStack Row="true" Spacing="4" Justify="Justify.SpaceEvenly" Style="width:100%">
<MudCard Elevation="0">
<MudText Typo="Typo.caption">@Localizer["Good"]</MudText>
<MudText Typo="Typo.body1" Style="font-weight: bold;">@totalGoods</MudText>
</MudCard>
<MudCard Elevation="0">
<MudText Typo="Typo.caption">@Localizer["OK"]</MudText>
<MudText Typo="Typo.body1" Style="font-weight: bold;">@totalOks</MudText>
</MudCard>
<MudCard Elevation="0">
<MudText Typo="Typo.caption">@Localizer["Bad"]</MudText>
<MudText Typo="Typo.body1" Style="font-weight: bold;">@totalBads</MudText>
</MudCard>
<MudCard Elevation="0">
<MudText Typo="Typo.caption">@Localizer["Drumroll"]</MudText>
<MudText Typo="Typo.body1" Style="font-weight: bold;">@totalDrumroll</MudText>
</MudCard>
<MudCard Elevation="0">
<MudText Typo="Typo.caption">@Localizer["MAX Combo"]</MudText>
<MudText Typo="Typo.body1" Style="font-weight: bold;">@totalMaxCombo</MudText>
</MudCard>
<MudCard Elevation="0">
<MudText Typo="Typo.caption">@Localizer["Total Hits"]</MudText>
<MudText Typo="Typo.body1" Style="font-weight: bold;">@totalHits</MudText>
</MudCard>
</MudStack>
</MudCardContent>
</MudCard>
</MudStack>
</MudItem>
</MudGrid>
<MudText Typo="Typo.h5" Class="mt-10 mb-4">@Localizer["Course Songs"]</MudText>
<MudGrid>
<MudItem xs="12">
<MudGrid Class="d-block">
@for (uint j = 0; j <= 2; j++)
{
var index = (int)j;
var danDataOdaiSong = danData.OdaiSongList[index];
var stageNumber = j + 1;
var difficulty = (Difficulty)danDataOdaiSong.Level;
<MudItem xs="12" Class="pb-1">
<MudCard Outlined="true" Class="pa-4">
<MudGrid Style="display:flex; align-items: center; justify-content: flex-start;">
<MudItem xs="1" md="1" Style="display:flex;flex-direction:column;align-items:center;">
<h3>@stageNumber</h3>
</MudItem>
<MudItem xs="2" md="1" Style="display:flex;flex-direction:column;align-items:center;">
<MudTooltip Text="@difficulty.ToString()" Placement="Placement.Top" Arrow="true">
<img src=@($"/images/difficulty_{difficulty}.webp") style="width:40px;height:40px;margin-bottom:2px;" alt="@difficulty" />
</MudTooltip>
<MudStack Row="true" Spacing="1" Justify="Justify.Center" AlignItems="AlignItems.Center">
<MudIcon Icon="@Icons.Material.Filled.Star" Size="Size.Small" />
<MudText Typo="Typo.caption" Style="line-height:1;margin-top:2px;margin-right:2px;">@GameDataService.GetMusicStarLevel(musicDetailDictionary, danDataOdaiSong.SongNo, difficulty)</MudText>
</MudStack>
</MudItem>
<MudItem xs="9" md="4" Style="display:flex;flex-direction:column;" Class="pl-4">
<MudText Typo="Typo.body1" Style="font-weight: bold;">@GameDataService.GetMusicNameBySongId(musicDetailDictionary, danDataOdaiSong.SongNo, SongNameLanguage)</MudText>
<MudText Typo="Typo.caption">@GameDataService.GetMusicArtistBySongId(musicDetailDictionary, danDataOdaiSong.SongNo, SongNameLanguage)</MudText>
</MudItem>
@if (_bestDataMap.TryGetValue(danId, out var danBestData))
{
if (danBestData.DanBestStageDataList.Count > index)
{
var bestStage = danBestData.DanBestStageDataList[index];
<MudItem xs="12" md="6" Style="display:flex;flex-direction:column;">
<MudStack Row="true" Spacing="4" Justify="Justify.SpaceEvenly">
<MudCard Elevation="0">
<MudText Typo="Typo.caption">@Localizer["Good"]</MudText>
<MudText Typo="Typo.body1" Style="font-weight: bold;">@bestStage.GoodCount</MudText>
</MudCard>
<MudCard Elevation="0">
<MudText Typo="Typo.caption">@Localizer["OK"]</MudText>
<MudText Typo="Typo.body1" Style="font-weight: bold;">@bestStage.OkCount</MudText>
</MudCard>
<MudCard Elevation="0">
<MudText Typo="Typo.caption">@Localizer["Bad"]</MudText>
<MudText Typo="Typo.body1" Style="font-weight: bold;">@bestStage.BadCount</MudText>
</MudCard>
<MudCard Elevation="0">
<MudText Typo="Typo.caption">@Localizer["Drumroll"]</MudText>
<MudText Typo="Typo.body1" Style="font-weight: bold;">@bestStage.DrumrollCount</MudText>
</MudCard>
<MudCard Elevation="0">
<MudText Typo="Typo.caption">@Localizer["MAX Combo"]</MudText>
<MudText Typo="Typo.body1" Style="font-weight: bold;">@bestStage.ComboCount</MudText>
</MudCard>
<MudCard Elevation="0">
<MudText Typo="Typo.caption">@Localizer["Total Hits"]</MudText>
<MudText Typo="Typo.body1" Style="font-weight: bold;">@bestStage.TotalHitCount</MudText>
</MudCard>
</MudStack>
</MudItem>
}
}
</MudGrid>
</MudCard>
</MudItem>
}
</MudGrid>
</MudItem>
</MudGrid>
<MudText Typo="Typo.h5" Class="mt-10 mb-4">@Localizer["Conditions"]</MudText>
<MudGrid>
<MudItem xs="12" Class="dani-results">
<MudGrid>
<MudItem xs="12" md="3">
<MudCard Outlined="true" Class="pa-2">
<MudCardHeader>
<CardHeaderContent>
<MudText Typo="Typo.h6">@Localizer["Soul Gauge"]</MudText>
</CardHeaderContent>
</MudCardHeader>
<MudCardContent>
<MudStack Spacing="8">
@{
var redRequirement = GetSoulGauge(danData, false);
var goldRequirement = GetSoulGauge(danData, true);
var barClass = "bar-default";
var resultText = Localizer["Not Passed"];
}
<MudStack Spacing="1">
<MudText Typo="Typo.subtitle2" Style="font-weight:bold;">@Localizer["Result"]</MudText>
@if (_bestDataMap.TryGetValue(danId, out var danBestData))
{
if (danBestData.SoulGaugeTotal >= redRequirement) {
barClass = "bar-pass-red";
resultText = Localizer["Pass"];
}
if (danBestData.SoulGaugeTotal >= goldRequirement) {
barClass = "bar-pass-gold";
resultText = Localizer["Gold"];
}
<MudProgressLinear Class="@barClass" Rounded="true" Size="Size.Large" Max="100" Value="@danBestData.SoulGaugeTotal">
<MudText Typo="Typo.caption">@danBestData.SoulGaugeTotal%</MudText>
</MudProgressLinear>
<MudText Typo="Typo.caption" Style="text-align: right">@resultText</MudText>
} else {
<MudProgressLinear Class="@barClass" Rounded="true" Size="Size.Large" Max="100" Value="0">
<MudText Typo="Typo.caption">0%</MudText>
</MudProgressLinear>
<MudText Typo="Typo.caption" Style="text-align: right">N/A</MudText>
}
</MudStack>
<MudStack Spacing="1">
<MudText Typo="Typo.subtitle2" Style="font-weight:bold">@Localizer["Conditions"]</MudText>
<MudStack Row="true" Spacing="16">
<MudStack Spacing="0">
<MudText Typo="Typo.caption">@Localizer["Red"]</MudText>
<MudText Typo="Typo.body1" Style="font-weight: bold">> @redRequirement%</MudText>
</MudStack>
<MudStack Spacing="0">
<MudText Typo="Typo.caption">@Localizer["Gold"]</MudText>
<MudText Typo="Typo.body1" Style="font-weight: bold">> @goldRequirement%</MudText>
</MudStack>
</MudStack>
</MudStack>
</MudStack>
</MudCardContent>
</MudCard>
</MudItem>
<MudItem xs="12" md="9">
<MudStack Spacing="4">
@for (var j = 1; j < danData.OdaiBorderList.Count; j++)
{
var border = danData.OdaiBorderList[j];
<MudCard Outlined="true" Class="pa-2">
<MudCardHeader>
<CardHeaderContent>
<MudText Typo="Typo.h6">
@GetDanRequirementTitle(border)
</MudText>
</CardHeaderContent>
</MudCardHeader>
<MudCardContent>
@{
var borderType = (DanBorderType)border.BorderType;
}
@if (borderType == DanBorderType.All)
{
<MudStack Spacing="8">
@{
var redRequirement = border.RedBorderTotal;
var goldRequirement = border.GoldBorderTotal;
var barClass = "bar-default";
var resultText = Localizer["Not Passed"];
}
<MudStack Spacing="1">
<MudText Typo="Typo.subtitle2" Style="font-weight:bold;">@Localizer["Result"]</MudText>
@if (_bestDataMap.TryGetValue(danId, out var danBestData))
{
var bestData = GetAllBestFromData((DanConditionType)border.OdaiType, danBestData);
if ((DanConditionType)border.OdaiType is DanConditionType.BadCount or DanConditionType.OkCount)
{
if (bestData <= goldRequirement)
{
barClass = "bar-pass-gold";
resultText = Localizer["Gold"];
}
else if (bestData <= redRequirement)
{
barClass = "bar-pass-red";
resultText = Localizer["Pass"];
}
var resultValue = redRequirement - bestData;
if (resultValue < 0) resultValue = 0;
<MudProgressLinear Class="@barClass" Rounded="true" Size="Size.Large" Max="@redRequirement" Value="@resultValue">
<MudText Typo="Typo.caption">@resultValue</MudText>
</MudProgressLinear>
<MudText Typo="Typo.caption" Style="text-align: right">@resultText</MudText>
}
else
{
if (bestData >= goldRequirement)
{
barClass = "bar-pass-gold";
resultText = Localizer["Gold"];
}
else if (bestData >= redRequirement)
{
barClass = "bar-pass-red";
resultText = Localizer["Pass"];
}
var resultValue = Math.Min(bestData, redRequirement);
<MudProgressLinear Class="@barClass" Rounded="true" Size="Size.Large" Max="@redRequirement" Value="@resultValue">
<MudText Typo="Typo.caption">@bestData</MudText>
</MudProgressLinear>
<MudText Typo="Typo.caption" Style="text-align: right">@resultText</MudText>
}
}
else
{
<MudProgressLinear Class="@barClass" Rounded="true" Size="Size.Large" Max="100" Value="0">
<MudText Typo="Typo.caption">0</MudText>
</MudProgressLinear>
<MudText Typo="Typo.caption" Style="text-align: right">N/A</MudText>
}
</MudStack>
@{
var conditionOperator = GetDanConditionOperator((DanConditionType)border.OdaiType);
}
<MudStack Spacing="1">
<MudText Typo="Typo.subtitle2" Style="font-weight:bold">@Localizer["Conditions"]</MudText>
<MudStack Row="true" Spacing="16">
<MudStack Spacing="0">
<MudText Typo="Typo.caption">@Localizer["Red"]</MudText>
<MudText Typo="Typo.body1" Style="font-weight: bold">@conditionOperator @redRequirement</MudText>
</MudStack>
<MudStack Spacing="0">
<MudText Typo="Typo.caption">@Localizer["Gold"]</MudText>
<MudText Typo="Typo.body1" Style="font-weight: bold">@conditionOperator @goldRequirement</MudText>
</MudStack>
</MudStack>
</MudStack>
</MudStack>
}
else
{
<MudGrid>
@for (var k = 0; k < 3; k++)
{
var songNumber = k;
var redRequirement = GetSongBorderCondition(border, songNumber, false);
var goldRequirement = GetSongBorderCondition(border, songNumber, true);
var barClass = "bar-default";
var resultText = Localizer["Not Cleared"];
<MudItem xs="12" md="4">
<MudCard Outlined="true">
<MudCardHeader>
<CardHeaderContent>
<MudText Typo="Typo.body1" Style="font-weight:bold">@Localizer["Stage"] @(songNumber + 1)</MudText>
</CardHeaderContent>
</MudCardHeader>
<MudCardContent>
<MudText Typo="Typo.subtitle2" Style="font-weight:bold;">@Localizer["Result"]</MudText>
@if (_bestDataMap.TryGetValue(danId, out var danBestData) && (danBestData.DanBestStageDataList.Count > songNumber))
{
var bestData = GetSongBestFromData((DanConditionType)border.OdaiType, danBestData, songNumber);
if ((DanConditionType)border.OdaiType is DanConditionType.BadCount or DanConditionType.OkCount)
{
if (bestData <= redRequirement)
{
barClass = "bar-pass-red";
resultText = Localizer["Pass"];
}
if (bestData <= goldRequirement)
{
barClass = "bar-pass-gold";
resultText = Localizer["Gold"];
}
var resultValue = redRequirement - bestData;
if (bestData >= redRequirement) resultValue = 0;
<MudProgressLinear Class="@barClass" Rounded="true" Size="Size.Large" Max="@redRequirement" Value="@resultValue">
<MudText Typo="Typo.caption">@resultValue</MudText>
</MudProgressLinear>
<MudText Typo="Typo.caption" Style="text-align: right">@resultText</MudText>
}
else
{
if (bestData >= redRequirement)
{
barClass = "bar-pass-red";
resultText = Localizer["Pass"];
}
if (bestData >= goldRequirement)
{
barClass = "bar-pass-gold";
resultText = Localizer["Gold"];
}
<MudProgressLinear Class="@barClass" Rounded="true" Size="Size.Large" Max="@(goldRequirement > 0 ? goldRequirement : 1)" Value="@(goldRequirement > 0 ? bestData : 1)">
<MudText Typo="Typo.caption">@bestData</MudText>
</MudProgressLinear>
<MudStack Class="mt-1" AlignItems="AlignItems.End">
<MudText Typo="Typo.caption">@resultText</MudText>
</MudStack>
}
}
else
{
<MudProgressLinear Class="@barClass" Rounded="true" Size="Size.Large" Max="100" Value="0">
<MudText Typo="Typo.caption">0</MudText>
</MudProgressLinear>
<MudStack Class="mt-1" AlignItems="AlignItems.End">
<MudText Typo="Typo.caption">N/A</MudText>
</MudStack>
}
@{
var conditionOperator = GetDanConditionOperator((DanConditionType)border.OdaiType);
if (redRequirement == 0) {
conditionOperator = "";
}
}
<MudStack Spacing="1" Class="mt-8">
<MudText Typo="Typo.subtitle2" Style="font-weight:bold">@Localizer["Conditions"]</MudText>
<MudStack Row="true" Spacing="16">
<MudStack Spacing="0">
<MudText Typo="Typo.caption">@Localizer["Red"]</MudText>
<MudText Typo="Typo.body1" Style="font-weight: bold">@conditionOperator @redRequirement</MudText>
</MudStack>
<MudStack Spacing="0">
<MudText Typo="Typo.caption">@Localizer["Gold"]</MudText>
<MudText Typo="Typo.body1" Style="font-weight: bold">@conditionOperator @goldRequirement</MudText>
</MudStack>
</MudStack>
</MudStack>
</MudCardContent>
</MudCard>
</MudItem>
}
</MudGrid>
}
</MudCardContent>
</MudCard>
}
</MudStack>
</MudItem>
</MudGrid>
</MudItem>
</MudGrid>
</MudTabPanel>
}
</MudTabs>
</MudPaper>
</MudItem>
</MudGrid>
}