Time weighted stats
This commit is contained in:
parent
e952edb7dc
commit
a726357f69
|
@ -1,4 +1,3 @@
|
|||
import 'dart:convert';
|
||||
import 'dart:math';
|
||||
import 'package:vector_math/vector_math_64.dart';
|
||||
|
||||
|
@ -151,10 +150,29 @@ class ReplayStats{
|
|||
}
|
||||
}
|
||||
|
||||
class AggregateStats{
|
||||
double apm;
|
||||
double pps;
|
||||
double vs;
|
||||
late NerdStats nerdStats;
|
||||
late EstTr estTr;
|
||||
late Playstyle playstyle;
|
||||
double spp;
|
||||
double kpp;
|
||||
double kps;
|
||||
|
||||
AggregateStats(this.apm, this.pps, this.vs, this.spp, this.kpp, this.kps){
|
||||
nerdStats = NerdStats(apm, pps, vs);
|
||||
estTr = EstTr(apm, pps, vs, nerdStats.app, nerdStats.dss, nerdStats.dsp, nerdStats.gbe);
|
||||
playstyle = Playstyle(apm, pps, nerdStats.app, nerdStats.vsapm, nerdStats.dsp, nerdStats.gbe, estTr.srarea, estTr.statrank);
|
||||
}
|
||||
}
|
||||
|
||||
class ReplayData{
|
||||
late String id;
|
||||
late Map<dynamic, dynamic> rawJson;
|
||||
late List<EndContextMulti> endcontext;
|
||||
late List<AggregateStats> timeWeightedStats;
|
||||
late List<List<ReplayStats>> stats;
|
||||
late List<ReplayStats> totalStats;
|
||||
late List<List<String>> roundWinners;
|
||||
|
@ -181,20 +199,45 @@ class ReplayData{
|
|||
totalLength = 0;
|
||||
stats = [];
|
||||
roundWinners = [];
|
||||
int roundID = 0;
|
||||
List<double> APMmultipliedByWeights = [0, 0];
|
||||
List<double> PPSmultipliedByWeights = [0, 0];
|
||||
List<double> VSmultipliedByWeights = [0, 0];
|
||||
List<double> SPPmultipliedByWeights = [0, 0];
|
||||
List<double> KPPmultipliedByWeights = [0, 0];
|
||||
List<double> KPSmultipliedByWeights = [0, 0];
|
||||
totalStats = [ReplayStats.createEmpty(), ReplayStats.createEmpty()];
|
||||
for(var round in json['data']) {
|
||||
int firstInEndContext = round['replays'][0]["events"].last['data']['export']['options']['gameid'].startsWith(endcontext[0].userId) ? 0 : 1;
|
||||
int secondInEndContext = round['replays'][1]["events"].last['data']['export']['options']['gameid'].startsWith(endcontext[1].userId) ? 1 : 0;
|
||||
roundLengths.add(max(round['replays'][0]['frames'], round['replays'][1]['frames']));
|
||||
int roundLength = max(round['replays'][0]['frames'], round['replays'][1]['frames']);
|
||||
roundLengths.add(roundLength);
|
||||
totalLength = totalLength + max(round['replays'][0]['frames'], round['replays'][1]['frames']);
|
||||
APMmultipliedByWeights[0] += endcontext[0].secondaryTracking[roundID]*roundLength;
|
||||
APMmultipliedByWeights[1] += endcontext[1].secondaryTracking[roundID]*roundLength;
|
||||
PPSmultipliedByWeights[0] += endcontext[0].tertiaryTracking[roundID]*roundLength;
|
||||
PPSmultipliedByWeights[1] += endcontext[1].tertiaryTracking[roundID]*roundLength;
|
||||
VSmultipliedByWeights[0] += endcontext[0].extraTracking[roundID]*roundLength;
|
||||
VSmultipliedByWeights[1] += endcontext[1].extraTracking[roundID]*roundLength;
|
||||
int winner = round['board'].indexWhere((element) => element['success'] == true);
|
||||
roundWinners.add([round['board'][winner]['id'], round['board'][winner]['username']]);
|
||||
ReplayStats playerOne = ReplayStats.fromJson(round['replays'][firstInEndContext]['events'].last['data']['export']['stats'], biggestSpikeFromReplay(round['replays'][secondInEndContext]['events']), round['replays'][firstInEndContext]['frames']); // (events contain recived attacks)
|
||||
ReplayStats playerTwo = ReplayStats.fromJson(round['replays'][secondInEndContext]['events'].last['data']['export']['stats'], biggestSpikeFromReplay(round['replays'][firstInEndContext]['events']), round['replays'][secondInEndContext]['frames']);
|
||||
SPPmultipliedByWeights[0] += playerOne.spp*roundLength;
|
||||
SPPmultipliedByWeights[1] += playerTwo.spp*roundLength;
|
||||
KPPmultipliedByWeights[0] += playerOne.kpp*roundLength;
|
||||
KPPmultipliedByWeights[1] += playerTwo.kpp*roundLength;
|
||||
KPSmultipliedByWeights[0] += playerOne.kps*roundLength;
|
||||
KPSmultipliedByWeights[1] += playerTwo.kps*roundLength;
|
||||
stats.add([playerOne, playerTwo]);
|
||||
totalStats[0] = totalStats[0] + playerOne;
|
||||
totalStats[1] = totalStats[1] + playerTwo;
|
||||
roundID ++;
|
||||
}
|
||||
timeWeightedStats = [
|
||||
AggregateStats(APMmultipliedByWeights[0]/totalLength, PPSmultipliedByWeights[0]/totalLength, VSmultipliedByWeights[0]/totalLength, SPPmultipliedByWeights[0]/totalLength, KPPmultipliedByWeights[0]/totalLength, KPSmultipliedByWeights[0]/totalLength),
|
||||
AggregateStats(APMmultipliedByWeights[1]/totalLength, PPSmultipliedByWeights[1]/totalLength, VSmultipliedByWeights[1]/totalLength, SPPmultipliedByWeights[1]/totalLength, KPPmultipliedByWeights[1]/totalLength, KPSmultipliedByWeights[1]/totalLength)
|
||||
];
|
||||
}
|
||||
|
||||
Map<String, dynamic> toJson(){
|
||||
|
|
|
@ -22,6 +22,9 @@ import 'package:window_manager/window_manager.dart';
|
|||
final DateFormat dateFormat = DateFormat.yMMMd(LocaleSettings.currentLocale.languageCode).add_Hms();
|
||||
int roundSelector = -1; // -1 = match averages, otherwise round number-1
|
||||
List<DropdownMenuItem> rounds = []; // index zero will be match stats
|
||||
bool timeWeightedStatsAvaliable = true;
|
||||
int greenSidePlayer = 0;
|
||||
int redSidePlayer = 1;
|
||||
late String oldWindowTitle;
|
||||
|
||||
Duration framesToTime(int frames){
|
||||
|
@ -60,403 +63,427 @@ class TlMatchResultState extends State<TlMatchResultView> {
|
|||
}
|
||||
|
||||
Widget buildComparison(bool bigScreen, bool showMobileSelector){
|
||||
return NestedScrollView(
|
||||
headerSliverBuilder: (context, value) {
|
||||
return [
|
||||
SliverToBoxAdapter(
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.fromLTRB(16, 16, 16, 32),
|
||||
child: Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Expanded(
|
||||
child: Container(
|
||||
decoration: BoxDecoration(
|
||||
gradient: LinearGradient(
|
||||
colors: const [Colors.green, Colors.transparent],
|
||||
begin: Alignment.bottomCenter,
|
||||
end: Alignment.topCenter,
|
||||
stops: [0.0, widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).success ? 0.4 : 0.0],
|
||||
)),
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.fromLTRB(8, 0, 8, 0),
|
||||
child: Column(children: [
|
||||
Text(widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).username, style: bigScreen ? const TextStyle(
|
||||
fontFamily: "Eurostile Round Extended",
|
||||
fontSize: 28) : const TextStyle()),
|
||||
Text(widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).points.toString(), style: const TextStyle(
|
||||
fontFamily: "Eurostile Round Extended",
|
||||
fontSize: 42))
|
||||
]),
|
||||
return FutureBuilder(future: replayData, builder: (context, snapshot){
|
||||
late Duration time;
|
||||
late String readableTime;
|
||||
late String reason;
|
||||
timeWeightedStatsAvaliable = true;
|
||||
if (snapshot.connectionState != ConnectionState.done) return const LinearProgressIndicator();
|
||||
if (!snapshot.hasError){
|
||||
if (rounds.indexWhere((element) => element.value == -2) == -1) rounds.insert(1, const DropdownMenuItem(value: -2, child: Text("timeWeightedStats")));
|
||||
greenSidePlayer = snapshot.data!.endcontext.indexWhere((element) => element.userId == widget.initPlayerId);
|
||||
redSidePlayer = snapshot.data!.endcontext.indexWhere((element) => element.userId != widget.initPlayerId);
|
||||
if (roundSelector.isNegative){
|
||||
time = framesToTime(snapshot.data!.totalLength);
|
||||
readableTime = "${t.matchLength}: ${time.inMinutes}:${secs.format(time.inMicroseconds /1000000 % 60)}";
|
||||
}else{
|
||||
time = framesToTime(snapshot.data!.roundLengths[roundSelector]);
|
||||
readableTime = "${t.roundLength}: ${time.inMinutes}:${secs.format(time.inMicroseconds /1000000 % 60)}\n${t.winner}: ${snapshot.data!.roundWinners[roundSelector][1]}";
|
||||
}
|
||||
}else{
|
||||
timeWeightedStatsAvaliable = false;
|
||||
switch (snapshot.error.runtimeType){
|
||||
case ReplayNotAvalable:
|
||||
reason = t.matchIsTooOld;
|
||||
break;
|
||||
case SzyNotFound:
|
||||
reason = t.matchIsTooOld;
|
||||
break;
|
||||
case SzyForbidden:
|
||||
reason = t.errors.replayRejected;
|
||||
break;
|
||||
case SzyTooManyRequests:
|
||||
reason = t.errors.tooManyRequests;
|
||||
break;
|
||||
default:
|
||||
reason = snapshot.error.toString();
|
||||
break;
|
||||
}
|
||||
}
|
||||
return NestedScrollView(
|
||||
headerSliverBuilder: (context, value) {
|
||||
return [
|
||||
SliverToBoxAdapter(
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.fromLTRB(16, 16, 16, 32),
|
||||
child: Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Expanded(
|
||||
child: Container(
|
||||
decoration: BoxDecoration(
|
||||
gradient: LinearGradient(
|
||||
colors: const [Colors.green, Colors.transparent],
|
||||
begin: Alignment.bottomCenter,
|
||||
end: Alignment.topCenter,
|
||||
stops: [0.0, widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).success ? 0.4 : 0.0],
|
||||
)),
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.fromLTRB(8, 0, 8, 0),
|
||||
child: Column(children: [
|
||||
Text(widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).username, style: bigScreen ? const TextStyle(
|
||||
fontFamily: "Eurostile Round Extended",
|
||||
fontSize: 28) : const TextStyle()),
|
||||
Text(widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).points.toString(), style: const TextStyle(
|
||||
fontFamily: "Eurostile Round Extended",
|
||||
fontSize: 42))
|
||||
]),
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
const Padding(
|
||||
padding: EdgeInsets.only(top: 16),
|
||||
child: Text("VS"),
|
||||
),
|
||||
Expanded(
|
||||
child: Container(
|
||||
decoration: BoxDecoration(
|
||||
gradient: LinearGradient(
|
||||
colors: const [Colors.red, Colors.transparent],
|
||||
begin: Alignment.bottomCenter,
|
||||
end: Alignment.topCenter,
|
||||
stops: [0.0, widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).success ? 0.4 : 0.0],
|
||||
)),
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.fromLTRB(8, 0, 8, 0),
|
||||
child: Column(children: [
|
||||
Text(widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).username, style: bigScreen ? const TextStyle(
|
||||
fontFamily: "Eurostile Round Extended",
|
||||
fontSize: 28) : const TextStyle()),
|
||||
Text(widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).points.toString(), style: const TextStyle(
|
||||
fontFamily: "Eurostile Round Extended",
|
||||
fontSize: 42))
|
||||
]),
|
||||
const Padding(
|
||||
padding: EdgeInsets.only(top: 16),
|
||||
child: Text("VS"),
|
||||
),
|
||||
Expanded(
|
||||
child: Container(
|
||||
decoration: BoxDecoration(
|
||||
gradient: LinearGradient(
|
||||
colors: const [Colors.red, Colors.transparent],
|
||||
begin: Alignment.bottomCenter,
|
||||
end: Alignment.topCenter,
|
||||
stops: [0.0, widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).success ? 0.4 : 0.0],
|
||||
)),
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.fromLTRB(8, 0, 8, 0),
|
||||
child: Column(children: [
|
||||
Text(widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).username, style: bigScreen ? const TextStyle(
|
||||
fontFamily: "Eurostile Round Extended",
|
||||
fontSize: 28) : const TextStyle()),
|
||||
Text(widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).points.toString(), style: const TextStyle(
|
||||
fontFamily: "Eurostile Round Extended",
|
||||
fontSize: 42))
|
||||
]),
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
],
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
if (showMobileSelector) SliverToBoxAdapter(
|
||||
child: Center(
|
||||
child: Row(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
crossAxisAlignment: CrossAxisAlignment.baseline,
|
||||
textBaseline: TextBaseline.alphabetic,
|
||||
children: [
|
||||
Text("${t.statsFor}: ",
|
||||
style: const TextStyle(color: Colors.white, fontSize: 25)),
|
||||
DropdownButton(items: rounds, value: roundSelector, onChanged: ((value) {
|
||||
roundSelector = value;
|
||||
setState(() {});
|
||||
}),),
|
||||
],
|
||||
if (showMobileSelector) SliverToBoxAdapter(
|
||||
child: Center(
|
||||
child: Row(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
crossAxisAlignment: CrossAxisAlignment.baseline,
|
||||
textBaseline: TextBaseline.alphabetic,
|
||||
children: [
|
||||
Text("${t.statsFor}: ",
|
||||
style: const TextStyle(color: Colors.white, fontSize: 25)),
|
||||
DropdownButton(items: rounds, value: roundSelector, onChanged: ((value) {
|
||||
roundSelector = value;
|
||||
setState(() {});
|
||||
}),),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
if (widget.record.ownId == widget.record.replayId && showMobileSelector) SliverToBoxAdapter(
|
||||
child: Center(child: Text(t.p1nkl0bst3rAlert, textAlign: TextAlign.center)),
|
||||
),
|
||||
if (showMobileSelector) SliverToBoxAdapter(child: FutureBuilder(future: replayData, builder: (context, snapshot) {
|
||||
switch(snapshot.connectionState){
|
||||
case ConnectionState.none:
|
||||
case ConnectionState.waiting:
|
||||
case ConnectionState.active:
|
||||
return const LinearProgressIndicator();
|
||||
case ConnectionState.done:
|
||||
if (!snapshot.hasError){
|
||||
if (roundSelector.isNegative){
|
||||
var time = framesToTime(snapshot.data!.totalLength);
|
||||
return Center(child: Text("${t.matchLength}: ${time.inMinutes}:${secs.format(time.inMicroseconds /1000000 % 60)}", textAlign: TextAlign.center));
|
||||
}else{
|
||||
var time = framesToTime(snapshot.data!.roundLengths[roundSelector]);
|
||||
return Center(child: Text("${t.roundLength}: ${time.inMinutes}:${secs.format(time.inMicroseconds /1000000 % 60)}\n${t.winner}: ${snapshot.data!.roundWinners[roundSelector][1]}", textAlign: TextAlign.center,));
|
||||
}
|
||||
}else{
|
||||
String reason;
|
||||
switch (snapshot.error.runtimeType){
|
||||
case ReplayNotAvalable:
|
||||
reason = t.matchIsTooOld;
|
||||
break;
|
||||
case SzyNotFound:
|
||||
reason = t.matchIsTooOld;
|
||||
break;
|
||||
case SzyForbidden:
|
||||
reason = t.errors.replayRejected;
|
||||
break;
|
||||
case SzyTooManyRequests:
|
||||
reason = t.errors.tooManyRequests;
|
||||
break;
|
||||
default:
|
||||
reason = snapshot.error.toString();
|
||||
break;
|
||||
}
|
||||
return Text("${t.replayIssue}: $reason", textAlign: TextAlign.center);
|
||||
}
|
||||
|
||||
}
|
||||
},),),
|
||||
const SliverToBoxAdapter(
|
||||
child: Divider(),
|
||||
)
|
||||
];
|
||||
},
|
||||
body: ListView(
|
||||
children: [
|
||||
Column(
|
||||
children: [
|
||||
CompareThingy(
|
||||
label: "APM",
|
||||
greenSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).secondary : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).secondaryTracking[roundSelector],
|
||||
redSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).secondary : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).secondaryTracking[roundSelector],
|
||||
fractionDigits: 2,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: "PPS",
|
||||
greenSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).tertiary : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).tertiaryTracking[roundSelector],
|
||||
redSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).tertiary : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).tertiaryTracking[roundSelector],
|
||||
fractionDigits: 2,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: "VS",
|
||||
greenSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).extra : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).extraTracking[roundSelector],
|
||||
redSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).extra : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).extraTracking[roundSelector],
|
||||
fractionDigits: 2,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
FutureBuilder(future: replayData, builder: (BuildContext context, AsyncSnapshot<ReplayData?> snapshot){
|
||||
switch(snapshot.connectionState){
|
||||
case ConnectionState.none:
|
||||
case ConnectionState.waiting:
|
||||
case ConnectionState.active:
|
||||
return const LinearProgressIndicator();
|
||||
case ConnectionState.done:
|
||||
if (!snapshot.hasError){
|
||||
var greenSidePlayer = snapshot.data!.endcontext.indexWhere((element) => element.userId == widget.initPlayerId);
|
||||
var redSidePlayer = snapshot.data!.endcontext.indexWhere((element) => element.userId != widget.initPlayerId);
|
||||
return Column(children: [
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].inputs : snapshot.data!.stats[roundSelector][greenSidePlayer].inputs,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].inputs : snapshot.data!.stats[roundSelector][redSidePlayer].inputs,
|
||||
label: "Inputs", higherIsBetter: true),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].piecesPlaced : snapshot.data!.stats[roundSelector][greenSidePlayer].piecesPlaced,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].piecesPlaced : snapshot.data!.stats[roundSelector][redSidePlayer].piecesPlaced,
|
||||
label: "Pieces Placed", higherIsBetter: true),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].kpp : snapshot.data!.stats[roundSelector][greenSidePlayer].kpp,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].kpp : snapshot.data!.stats[roundSelector][redSidePlayer].kpp,
|
||||
label: "KpP", higherIsBetter: false, fractionDigits: 2,),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].kps : snapshot.data!.stats[roundSelector][greenSidePlayer].kps,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].kps : snapshot.data!.stats[roundSelector][redSidePlayer].kps,
|
||||
label: "KpS", higherIsBetter: true, fractionDigits: 2,),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].linesCleared : snapshot.data!.stats[roundSelector][greenSidePlayer].linesCleared,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].linesCleared : snapshot.data!.stats[roundSelector][redSidePlayer].linesCleared,
|
||||
label: "Lines Cleared", higherIsBetter: true),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].score : snapshot.data!.stats[roundSelector][greenSidePlayer].score,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].score : snapshot.data!.stats[roundSelector][redSidePlayer].score,
|
||||
label: "Score", higherIsBetter: true),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].spp : snapshot.data!.stats[roundSelector][greenSidePlayer].spp,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].spp : snapshot.data!.stats[roundSelector][redSidePlayer].spp,
|
||||
label: "SpP", higherIsBetter: true, fractionDigits: 2,),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].finessePercentage * 100 : snapshot.data!.stats[roundSelector][greenSidePlayer].finessePercentage * 100,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].finessePercentage * 100 : snapshot.data!.stats[roundSelector][redSidePlayer].finessePercentage * 100,
|
||||
label: "Finnese", postfix: "%", fractionDigits: 2, higherIsBetter: true),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].topSpike : snapshot.data!.stats[roundSelector][greenSidePlayer].topSpike,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].topSpike : snapshot.data!.stats[roundSelector][redSidePlayer].topSpike,
|
||||
label: "Best Spike", higherIsBetter: true),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].topCombo : snapshot.data!.stats[roundSelector][greenSidePlayer].topCombo,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].topCombo : snapshot.data!.stats[roundSelector][redSidePlayer].topCombo,
|
||||
label: "Best Combo", higherIsBetter: true),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].topBtB : snapshot.data!.stats[roundSelector][greenSidePlayer].topBtB,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].topBtB : snapshot.data!.stats[roundSelector][redSidePlayer].topBtB,
|
||||
label: "Best BtB", higherIsBetter: true),
|
||||
const Divider(),
|
||||
Padding(
|
||||
padding: const EdgeInsets.only(bottom: 16),
|
||||
child: Text("Garbage", style: TextStyle(fontFamily: "Eurostile Round Extended", fontSize: bigScreen ? 42 : 28)),
|
||||
),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].garbage.sent : snapshot.data!.stats[roundSelector][greenSidePlayer].garbage.sent,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].garbage.sent : snapshot.data!.stats[roundSelector][redSidePlayer].garbage.sent,
|
||||
label: "Sent", higherIsBetter: true),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].garbage.recived : snapshot.data!.stats[roundSelector][greenSidePlayer].garbage.recived,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].garbage.recived : snapshot.data!.stats[roundSelector][redSidePlayer].garbage.recived,
|
||||
label: "Recived", higherIsBetter: true),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].garbage.attack : snapshot.data!.stats[roundSelector][greenSidePlayer].garbage.attack,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].garbage.attack : snapshot.data!.stats[roundSelector][redSidePlayer].garbage.attack,
|
||||
label: "Attack", higherIsBetter: true),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].garbage.cleared : snapshot.data!.stats[roundSelector][greenSidePlayer].garbage.cleared,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].garbage.cleared : snapshot.data!.stats[roundSelector][redSidePlayer].garbage.cleared,
|
||||
label: "Cleared", higherIsBetter: true),
|
||||
const Divider(),
|
||||
Padding(
|
||||
padding: const EdgeInsets.only(bottom: 16),
|
||||
child: Text("Line Clears", style: TextStyle(fontFamily: "Eurostile Round Extended", fontSize: bigScreen ? 42 : 28)),
|
||||
),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].clears.allClears : snapshot.data!.stats[roundSelector][greenSidePlayer].clears.allClears,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].clears.allClears : snapshot.data!.stats[roundSelector][redSidePlayer].clears.allClears,
|
||||
label: "PC", higherIsBetter: true),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].tspins : snapshot.data!.stats[roundSelector][greenSidePlayer].tspins,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].tspins : snapshot.data!.stats[roundSelector][redSidePlayer].tspins,
|
||||
label: "T-spins", higherIsBetter: true),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].clears.quads : snapshot.data!.stats[roundSelector][greenSidePlayer].clears.quads,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].clears.quads : snapshot.data!.stats[roundSelector][redSidePlayer].clears.quads,
|
||||
label: "Quads", higherIsBetter: true),
|
||||
],);
|
||||
}else{
|
||||
return Container();
|
||||
}
|
||||
|
||||
}
|
||||
})
|
||||
],
|
||||
),
|
||||
const Divider(),
|
||||
Column(
|
||||
children: [
|
||||
Padding(
|
||||
padding: const EdgeInsets.only(bottom: 16),
|
||||
child: Text(t.nerdStats,
|
||||
style: TextStyle(
|
||||
fontFamily: "Eurostile Round Extended",
|
||||
fontSize: bigScreen ? 42 : 28)),
|
||||
),
|
||||
CompareThingy(
|
||||
label: "APP",
|
||||
greenSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStats.app : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStatsTracking[roundSelector].app,
|
||||
redSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStats.app : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStatsTracking[roundSelector].app,
|
||||
fractionDigits: 3,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: "VS/APM",
|
||||
greenSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStats.vsapm : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStatsTracking[roundSelector].vsapm,
|
||||
redSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStats.vsapm : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStatsTracking[roundSelector].vsapm,
|
||||
fractionDigits: 3,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: "DS/S",
|
||||
greenSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStats.dss : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStatsTracking[roundSelector].dss,
|
||||
redSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStats.dss : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStatsTracking[roundSelector].dss,
|
||||
fractionDigits: 3,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: "DS/P",
|
||||
greenSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStats.dsp : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStatsTracking[roundSelector].dsp,
|
||||
redSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStats.dsp : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStatsTracking[roundSelector].dsp,
|
||||
fractionDigits: 3,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: "APP + DS/P",
|
||||
greenSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStats.appdsp : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStatsTracking[roundSelector].appdsp,
|
||||
redSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStats.appdsp : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStatsTracking[roundSelector].appdsp,
|
||||
fractionDigits: 3,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: t.statCellNum.cheese.replaceAll(RegExp(r'\n'), " "),
|
||||
greenSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStats.cheese : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStatsTracking[roundSelector].cheese,
|
||||
redSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStats.cheese : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStatsTracking[roundSelector].cheese,
|
||||
fractionDigits: 2,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: "Gb Eff.",
|
||||
greenSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStats.gbe : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStatsTracking[roundSelector].gbe,
|
||||
redSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStats.gbe : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStatsTracking[roundSelector].gbe,
|
||||
fractionDigits: 3,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: "wAPP",
|
||||
greenSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStats.nyaapp : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStatsTracking[roundSelector].nyaapp,
|
||||
redSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStats.nyaapp : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStatsTracking[roundSelector].nyaapp,
|
||||
fractionDigits: 3,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: "Area",
|
||||
greenSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStats.area : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStatsTracking[roundSelector].area,
|
||||
redSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStats.area : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStatsTracking[roundSelector].area,
|
||||
fractionDigits: 2,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: t.statCellNum.estOfTRShort,
|
||||
greenSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).estTr.esttr : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).estTrTracking[roundSelector].esttr,
|
||||
redSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).estTr.esttr : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).estTrTracking[roundSelector].esttr,
|
||||
fractionDigits: 2,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: "Opener",
|
||||
greenSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).playstyle.opener : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).playstyleTracking[roundSelector].opener,
|
||||
redSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).playstyle.opener : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).playstyleTracking[roundSelector].opener,
|
||||
fractionDigits: 3,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: "Plonk",
|
||||
greenSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).playstyle.plonk : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).playstyleTracking[roundSelector].plonk,
|
||||
redSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).playstyle.plonk : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).playstyleTracking[roundSelector].plonk,
|
||||
fractionDigits: 3,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: "Stride",
|
||||
greenSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).playstyle.stride : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).playstyleTracking[roundSelector].stride,
|
||||
redSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).playstyle.stride : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).playstyleTracking[roundSelector].stride,
|
||||
fractionDigits: 3,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: "Inf. DS",
|
||||
greenSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).playstyle.infds : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).playstyleTracking[roundSelector].infds,
|
||||
redSide: roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).playstyle.infds : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).playstyleTracking[roundSelector].infds,
|
||||
fractionDigits: 3,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
VsGraphs(
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).secondary : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).secondaryTracking[roundSelector],
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).tertiary : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).tertiaryTracking[roundSelector],
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).extra : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).extraTracking[roundSelector],
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStats : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStatsTracking[roundSelector],
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).playstyle : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).playstyleTracking[roundSelector],
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).secondary : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).secondaryTracking[roundSelector],
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).tertiary : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).tertiaryTracking[roundSelector],
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).extra : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).extraTracking[roundSelector],
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStats : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStatsTracking[roundSelector],
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).playstyle : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).playstyleTracking[roundSelector]
|
||||
)
|
||||
],
|
||||
),
|
||||
if (widget.record.ownId != widget.record.replayId) const Divider(),
|
||||
if (widget.record.ownId != widget.record.replayId) Column(
|
||||
children: [
|
||||
Padding(
|
||||
padding: const EdgeInsets.only(bottom: 16),
|
||||
child: Text("Handling",
|
||||
style: TextStyle(
|
||||
fontFamily: "Eurostile Round Extended",
|
||||
fontSize: bigScreen ? 42 : 28)),
|
||||
),
|
||||
CompareThingy(
|
||||
greenSide: widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).handling.das,
|
||||
redSide: widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).handling.das,
|
||||
label: "DAS", fractionDigits: 1, postfix: "F",
|
||||
higherIsBetter: false),
|
||||
CompareThingy(
|
||||
greenSide: widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).handling.arr,
|
||||
redSide: widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).handling.arr,
|
||||
label: "ARR", fractionDigits: 1, postfix: "F",
|
||||
higherIsBetter: false),
|
||||
CompareThingy(
|
||||
greenSide: widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).handling.sdf,
|
||||
redSide: widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).handling.sdf,
|
||||
label: "SDF", prefix: "x",
|
||||
higherIsBetter: true),
|
||||
CompareBoolThingy(
|
||||
greenSide: widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).handling.safeLock,
|
||||
redSide: widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).handling.safeLock,
|
||||
label: "Safe HD",
|
||||
trueIsBetter: true)
|
||||
],
|
||||
)
|
||||
],
|
||||
if (widget.record.ownId == widget.record.replayId && showMobileSelector) SliverToBoxAdapter(
|
||||
child: Center(child: Text(t.p1nkl0bst3rAlert, textAlign: TextAlign.center)),
|
||||
),
|
||||
if (showMobileSelector) SliverToBoxAdapter(child: Center(child: Text(snapshot.hasError ? reason : readableTime, textAlign: TextAlign.center))),
|
||||
const SliverToBoxAdapter(
|
||||
child: Divider(),
|
||||
)
|
||||
);
|
||||
];
|
||||
},
|
||||
body: ListView(
|
||||
children: [
|
||||
Column(
|
||||
children: [
|
||||
CompareThingy(
|
||||
label: "APM",
|
||||
greenSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[greenSidePlayer].apm :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).secondary : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).secondaryTracking[roundSelector],
|
||||
redSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[redSidePlayer].apm :
|
||||
roundSelector == -1 ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).secondary : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).secondaryTracking[roundSelector],
|
||||
fractionDigits: 2,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: "PPS",
|
||||
greenSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[greenSidePlayer].pps:
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).tertiary : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).tertiaryTracking[roundSelector],
|
||||
redSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[redSidePlayer].pps :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).tertiary: widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).tertiaryTracking[roundSelector],
|
||||
fractionDigits: 2,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: "VS",
|
||||
greenSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[greenSidePlayer].vs :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).extra : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).extraTracking[roundSelector],
|
||||
redSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[redSidePlayer].vs :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).extra : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).extraTracking[roundSelector],
|
||||
fractionDigits: 2,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
if (snapshot.hasData) Column(children: [
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].inputs : snapshot.data!.stats[roundSelector][greenSidePlayer].inputs,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].inputs : snapshot.data!.stats[roundSelector][redSidePlayer].inputs,
|
||||
label: "Inputs", higherIsBetter: true),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].piecesPlaced : snapshot.data!.stats[roundSelector][greenSidePlayer].piecesPlaced,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].piecesPlaced : snapshot.data!.stats[roundSelector][redSidePlayer].piecesPlaced,
|
||||
label: "Pieces Placed", higherIsBetter: true),
|
||||
CompareThingy(greenSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[greenSidePlayer].kpp :
|
||||
roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].kpp : snapshot.data!.stats[roundSelector][greenSidePlayer].kpp,
|
||||
redSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[redSidePlayer].kpp :
|
||||
roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].kpp : snapshot.data!.stats[roundSelector][redSidePlayer].kpp,
|
||||
label: "KpP", higherIsBetter: false, fractionDigits: 2,),
|
||||
CompareThingy(greenSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[greenSidePlayer].kps :
|
||||
roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].kps : snapshot.data!.stats[roundSelector][greenSidePlayer].kps,
|
||||
redSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[redSidePlayer].kps :
|
||||
roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].kps : snapshot.data!.stats[roundSelector][redSidePlayer].kps,
|
||||
label: "KpS", higherIsBetter: true, fractionDigits: 2,),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].linesCleared : snapshot.data!.stats[roundSelector][greenSidePlayer].linesCleared,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].linesCleared : snapshot.data!.stats[roundSelector][redSidePlayer].linesCleared,
|
||||
label: "Lines Cleared", higherIsBetter: true),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].score : snapshot.data!.stats[roundSelector][greenSidePlayer].score,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].score : snapshot.data!.stats[roundSelector][redSidePlayer].score,
|
||||
label: "Score", higherIsBetter: true),
|
||||
CompareThingy(greenSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[greenSidePlayer].spp :
|
||||
roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].spp : snapshot.data!.stats[roundSelector][greenSidePlayer].spp,
|
||||
redSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[redSidePlayer].spp :
|
||||
roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].spp : snapshot.data!.stats[roundSelector][redSidePlayer].spp,
|
||||
label: "SpP", higherIsBetter: true, fractionDigits: 2,),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].finessePercentage * 100 : snapshot.data!.stats[roundSelector][greenSidePlayer].finessePercentage * 100,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].finessePercentage * 100 : snapshot.data!.stats[roundSelector][redSidePlayer].finessePercentage * 100,
|
||||
label: "Finnese", postfix: "%", fractionDigits: 2, higherIsBetter: true),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].topSpike : snapshot.data!.stats[roundSelector][greenSidePlayer].topSpike,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].topSpike : snapshot.data!.stats[roundSelector][redSidePlayer].topSpike,
|
||||
label: "Best Spike", higherIsBetter: true),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].topCombo : snapshot.data!.stats[roundSelector][greenSidePlayer].topCombo,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].topCombo : snapshot.data!.stats[roundSelector][redSidePlayer].topCombo,
|
||||
label: "Best Combo", higherIsBetter: true),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].topBtB : snapshot.data!.stats[roundSelector][greenSidePlayer].topBtB,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].topBtB : snapshot.data!.stats[roundSelector][redSidePlayer].topBtB,
|
||||
label: "Best BtB", higherIsBetter: true),
|
||||
const Divider(),
|
||||
Padding(
|
||||
padding: const EdgeInsets.only(bottom: 16),
|
||||
child: Text("Garbage", style: TextStyle(fontFamily: "Eurostile Round Extended", fontSize: bigScreen ? 42 : 28)),
|
||||
),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].garbage.sent : snapshot.data!.stats[roundSelector][greenSidePlayer].garbage.sent,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].garbage.sent : snapshot.data!.stats[roundSelector][redSidePlayer].garbage.sent,
|
||||
label: "Sent", higherIsBetter: true),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].garbage.recived : snapshot.data!.stats[roundSelector][greenSidePlayer].garbage.recived,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].garbage.recived : snapshot.data!.stats[roundSelector][redSidePlayer].garbage.recived,
|
||||
label: "Recived", higherIsBetter: true),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].garbage.attack : snapshot.data!.stats[roundSelector][greenSidePlayer].garbage.attack,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].garbage.attack : snapshot.data!.stats[roundSelector][redSidePlayer].garbage.attack,
|
||||
label: "Attack", higherIsBetter: true),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].garbage.cleared : snapshot.data!.stats[roundSelector][greenSidePlayer].garbage.cleared,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].garbage.cleared : snapshot.data!.stats[roundSelector][redSidePlayer].garbage.cleared,
|
||||
label: "Cleared", higherIsBetter: true),
|
||||
const Divider(),
|
||||
Padding(
|
||||
padding: const EdgeInsets.only(bottom: 16),
|
||||
child: Text("Line Clears", style: TextStyle(fontFamily: "Eurostile Round Extended", fontSize: bigScreen ? 42 : 28)),
|
||||
),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].clears.allClears : snapshot.data!.stats[roundSelector][greenSidePlayer].clears.allClears,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].clears.allClears : snapshot.data!.stats[roundSelector][redSidePlayer].clears.allClears,
|
||||
label: "PC", higherIsBetter: true),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].tspins : snapshot.data!.stats[roundSelector][greenSidePlayer].tspins,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].tspins : snapshot.data!.stats[roundSelector][redSidePlayer].tspins,
|
||||
label: "T-spins", higherIsBetter: true),
|
||||
CompareThingy(greenSide: roundSelector.isNegative ? snapshot.data!.totalStats[greenSidePlayer].clears.quads : snapshot.data!.stats[roundSelector][greenSidePlayer].clears.quads,
|
||||
redSide: roundSelector.isNegative ? snapshot.data!.totalStats[redSidePlayer].clears.quads : snapshot.data!.stats[roundSelector][redSidePlayer].clears.quads,
|
||||
label: "Quads", higherIsBetter: true),
|
||||
],),
|
||||
],
|
||||
),
|
||||
const Divider(),
|
||||
Column(
|
||||
children: [
|
||||
Padding(
|
||||
padding: const EdgeInsets.only(bottom: 16),
|
||||
child: Text(t.nerdStats,
|
||||
style: TextStyle(
|
||||
fontFamily: "Eurostile Round Extended",
|
||||
fontSize: bigScreen ? 42 : 28)),
|
||||
),
|
||||
CompareThingy(
|
||||
label: "APP",
|
||||
greenSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[greenSidePlayer].nerdStats.app :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStats.app : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStatsTracking[roundSelector].app,
|
||||
redSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[redSidePlayer].nerdStats.app :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStats.app : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStatsTracking[roundSelector].app,
|
||||
fractionDigits: 3,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: "VS/APM",
|
||||
greenSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[greenSidePlayer].nerdStats.vsapm :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStats.vsapm : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStatsTracking[roundSelector].vsapm,
|
||||
redSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[redSidePlayer].nerdStats.vsapm :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStats.vsapm : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStatsTracking[roundSelector].vsapm,
|
||||
fractionDigits: 3,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: "DS/S",
|
||||
greenSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[greenSidePlayer].nerdStats.dss :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStats.dss : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStatsTracking[roundSelector].dss,
|
||||
redSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[redSidePlayer].nerdStats.dss :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStats.dss : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStatsTracking[roundSelector].dss,
|
||||
fractionDigits: 3,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: "DS/P",
|
||||
greenSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[greenSidePlayer].nerdStats.dsp :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStats.dsp : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStatsTracking[roundSelector].dsp,
|
||||
redSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[redSidePlayer].nerdStats.dsp :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStats.dsp : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStatsTracking[roundSelector].dsp,
|
||||
fractionDigits: 3,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: "APP + DS/P",
|
||||
greenSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[greenSidePlayer].nerdStats.appdsp :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStats.appdsp : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStatsTracking[roundSelector].appdsp,
|
||||
redSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[redSidePlayer].nerdStats.appdsp :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStats.appdsp : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStatsTracking[roundSelector].appdsp,
|
||||
fractionDigits: 3,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: t.statCellNum.cheese.replaceAll(RegExp(r'\n'), " "),
|
||||
greenSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[greenSidePlayer].nerdStats.cheese :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStats.cheese : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStatsTracking[roundSelector].cheese,
|
||||
redSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[redSidePlayer].nerdStats.cheese :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStats.cheese : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStatsTracking[roundSelector].cheese,
|
||||
fractionDigits: 2,
|
||||
higherIsBetter: false,
|
||||
),
|
||||
CompareThingy(
|
||||
label: "Gb Eff.",
|
||||
greenSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[greenSidePlayer].nerdStats.gbe :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStats.gbe : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStatsTracking[roundSelector].gbe,
|
||||
redSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[redSidePlayer].nerdStats.gbe :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStats.gbe : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStatsTracking[roundSelector].gbe,
|
||||
fractionDigits: 3,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: "wAPP",
|
||||
greenSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[greenSidePlayer].nerdStats.nyaapp :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStats.nyaapp : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStatsTracking[roundSelector].nyaapp,
|
||||
redSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[redSidePlayer].nerdStats.nyaapp :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStats.nyaapp : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStatsTracking[roundSelector].nyaapp,
|
||||
fractionDigits: 3,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: "Area",
|
||||
greenSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[greenSidePlayer].nerdStats.area :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStats.area : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStatsTracking[roundSelector].area,
|
||||
redSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[redSidePlayer].nerdStats.area :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStats.area : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStatsTracking[roundSelector].area,
|
||||
fractionDigits: 2,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: t.statCellNum.estOfTRShort,
|
||||
greenSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[greenSidePlayer].estTr.esttr :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).estTr.esttr : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).estTrTracking[roundSelector].esttr,
|
||||
redSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[redSidePlayer].estTr.esttr :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).estTr.esttr : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).estTrTracking[roundSelector].esttr,
|
||||
fractionDigits: 2,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: "Opener",
|
||||
greenSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[greenSidePlayer].playstyle.opener :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).playstyle.opener : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).playstyleTracking[roundSelector].opener,
|
||||
redSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[redSidePlayer].playstyle.opener :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).playstyle.opener : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).playstyleTracking[roundSelector].opener,
|
||||
fractionDigits: 3,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: "Plonk",
|
||||
greenSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[greenSidePlayer].playstyle.plonk :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).playstyle.plonk : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).playstyleTracking[roundSelector].plonk,
|
||||
redSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[redSidePlayer].playstyle.plonk :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).playstyle.plonk : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).playstyleTracking[roundSelector].plonk,
|
||||
fractionDigits: 3,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: "Stride",
|
||||
greenSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[greenSidePlayer].playstyle.stride :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).playstyle.stride : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).playstyleTracking[roundSelector].stride,
|
||||
redSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[redSidePlayer].playstyle.stride :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).playstyle.stride : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).playstyleTracking[roundSelector].stride,
|
||||
fractionDigits: 3,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
CompareThingy(
|
||||
label: "Inf. DS",
|
||||
greenSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[greenSidePlayer].playstyle.infds :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).playstyle.infds : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).playstyleTracking[roundSelector].infds,
|
||||
redSide: (roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[redSidePlayer].playstyle.infds :
|
||||
roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).playstyle.infds : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).playstyleTracking[roundSelector].infds,
|
||||
fractionDigits: 3,
|
||||
higherIsBetter: true,
|
||||
),
|
||||
VsGraphs(
|
||||
(roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[greenSidePlayer].apm : roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).secondary : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).secondaryTracking[roundSelector],
|
||||
(roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[greenSidePlayer].pps : roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).tertiary : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).tertiaryTracking[roundSelector],
|
||||
(roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[greenSidePlayer].vs : roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).extra : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).extraTracking[roundSelector],
|
||||
(roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[greenSidePlayer].nerdStats : roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStats : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).nerdStatsTracking[roundSelector],
|
||||
(roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[greenSidePlayer].playstyle : roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).playstyle : widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).playstyleTracking[roundSelector],
|
||||
(roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[redSidePlayer].apm : roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).secondary : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).secondaryTracking[roundSelector],
|
||||
(roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[redSidePlayer].pps : roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).tertiary : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).tertiaryTracking[roundSelector],
|
||||
(roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[redSidePlayer].vs : roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).extra : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).extraTracking[roundSelector],
|
||||
(roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[redSidePlayer].nerdStats : roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStats : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).nerdStatsTracking[roundSelector],
|
||||
(roundSelector == -2 && snapshot.hasData) ? snapshot.data!.timeWeightedStats[redSidePlayer].playstyle : roundSelector.isNegative ? widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).playstyle : widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).playstyleTracking[roundSelector]
|
||||
)
|
||||
],
|
||||
),
|
||||
if (widget.record.ownId != widget.record.replayId) const Divider(),
|
||||
if (widget.record.ownId != widget.record.replayId) Column(
|
||||
children: [
|
||||
Padding(
|
||||
padding: const EdgeInsets.only(bottom: 16),
|
||||
child: Text("Handling",
|
||||
style: TextStyle(
|
||||
fontFamily: "Eurostile Round Extended",
|
||||
fontSize: bigScreen ? 42 : 28)),
|
||||
),
|
||||
CompareThingy(
|
||||
greenSide: widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).handling.das,
|
||||
redSide: widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).handling.das,
|
||||
label: "DAS", fractionDigits: 1, postfix: "F",
|
||||
higherIsBetter: false),
|
||||
CompareThingy(
|
||||
greenSide: widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).handling.arr,
|
||||
redSide: widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).handling.arr,
|
||||
label: "ARR", fractionDigits: 1, postfix: "F",
|
||||
higherIsBetter: false),
|
||||
CompareThingy(
|
||||
greenSide: widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).handling.sdf,
|
||||
redSide: widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).handling.sdf,
|
||||
label: "SDF", prefix: "x",
|
||||
higherIsBetter: true),
|
||||
CompareBoolThingy(
|
||||
greenSide: widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).handling.safeLock,
|
||||
redSide: widget.record.endContext.firstWhere((element) => element.userId != widget.initPlayerId).handling.safeLock,
|
||||
label: "Safe HD",
|
||||
trueIsBetter: true)
|
||||
],
|
||||
)
|
||||
],
|
||||
)
|
||||
);
|
||||
});
|
||||
}
|
||||
|
||||
Widget buildRoundSelector(double width){
|
||||
return Padding(
|
||||
padding: EdgeInsets.all(8.0000000),
|
||||
padding: const EdgeInsets.all(8.000000),
|
||||
child: SizedBox(
|
||||
width: width,
|
||||
child: NestedScrollView(
|
||||
|
@ -482,8 +509,8 @@ class TlMatchResultState extends State<TlMatchResultView> {
|
|||
RichText(
|
||||
text: TextSpan(
|
||||
text: "${time.inMinutes}:${NumberFormat("00", LocaleSettings.currentLocale.languageCode).format(time.inSeconds%60)}",
|
||||
style: TextStyle(fontFamily: "Eurostile Round Extended", fontSize: 28, fontWeight: FontWeight.w500),
|
||||
children: [TextSpan(text: ".${NumberFormat("000", LocaleSettings.currentLocale.languageCode).format(time.inMilliseconds%1000)}", style: TextStyle(fontFamily: "Eurostile Round", fontSize: 14, fontWeight: FontWeight.w100))]
|
||||
style: const TextStyle(fontFamily: "Eurostile Round Extended", fontSize: 28, fontWeight: FontWeight.w500),
|
||||
children: [TextSpan(text: ".${NumberFormat("000", LocaleSettings.currentLocale.languageCode).format(time.inMilliseconds%1000)}", style: const TextStyle(fontFamily: "Eurostile Round", fontSize: 14, fontWeight: FontWeight.w100))]
|
||||
),
|
||||
)
|
||||
],);
|
||||
|
@ -512,7 +539,7 @@ class TlMatchResultState extends State<TlMatchResultView> {
|
|||
if (widget.record.ownId != widget.record.replayId) Text("${t.replayIssue}: $reason"),
|
||||
if (widget.record.ownId == widget.record.replayId) Center(child: Text(t.p1nkl0bst3rAlert, textAlign: TextAlign.center)),
|
||||
if (widget.record.ownId != widget.record.replayId) RichText(
|
||||
text: TextSpan(
|
||||
text: const TextSpan(
|
||||
text: "-:--",
|
||||
style: TextStyle(fontFamily: "Eurostile Round Extended", fontSize: 28, fontWeight: FontWeight.w500, color: Colors.grey),
|
||||
children: [TextSpan(text: ".---", style: TextStyle(fontFamily: "Eurostile Round", fontSize: 14, fontWeight: FontWeight.w100))]
|
||||
|
@ -526,7 +553,7 @@ class TlMatchResultState extends State<TlMatchResultView> {
|
|||
if (widget.record.ownId != widget.record.replayId) Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.end,
|
||||
children: [
|
||||
Text("Number of rounds"),
|
||||
const Text("Number of rounds"),
|
||||
RichText(
|
||||
text: TextSpan(
|
||||
text: widget.record.endContext.first.secondaryTracking.length > 0 ? widget.record.endContext.first.secondaryTracking.length.toString() : "---",
|
||||
|
@ -549,10 +576,12 @@ class TlMatchResultState extends State<TlMatchResultView> {
|
|||
roundSelector = -1;
|
||||
setState(() {});
|
||||
}),
|
||||
TextButton( child: const Text('Time-weighted match stats'), onPressed: () {
|
||||
roundSelector = -1;
|
||||
TextButton( child: const Text('Time-weighted match stats'),
|
||||
style: roundSelector == -2 ? ButtonStyle(backgroundColor: MaterialStatePropertyAll(Colors.grey.shade900)) : null,
|
||||
onPressed: timeWeightedStatsAvaliable ? () {
|
||||
roundSelector = -2;
|
||||
setState(() {});
|
||||
}),
|
||||
} : null) ,
|
||||
//TextButton( child: const Text('Button 3'), onPressed: () {}),
|
||||
],
|
||||
)
|
||||
|
@ -595,8 +624,8 @@ class TlMatchResultState extends State<TlMatchResultView> {
|
|||
leading:RichText(
|
||||
text: TextSpan(
|
||||
text: "${time.inMinutes}:${NumberFormat("00", LocaleSettings.currentLocale.languageCode).format(time.inSeconds%60)}",
|
||||
style: TextStyle(fontFamily: "Eurostile Round", fontSize: 22, fontWeight: FontWeight.w500),
|
||||
children: [TextSpan(text: ".${NumberFormat("000", LocaleSettings.currentLocale.languageCode).format(time.inMilliseconds%1000)}", style: TextStyle(fontFamily: "Eurostile Round", fontSize: 14, fontWeight: FontWeight.w100))]
|
||||
style: const TextStyle(fontFamily: "Eurostile Round", fontSize: 22, fontWeight: FontWeight.w500),
|
||||
children: [TextSpan(text: ".${NumberFormat("000", LocaleSettings.currentLocale.languageCode).format(time.inMilliseconds%1000)}", style: const TextStyle(fontFamily: "Eurostile Round", fontSize: 14, fontWeight: FontWeight.w100))]
|
||||
),
|
||||
),
|
||||
title: Text(snapshot.data!.roundWinners[index][1], textAlign: TextAlign.center),
|
||||
|
@ -621,13 +650,13 @@ class TlMatchResultState extends State<TlMatchResultView> {
|
|||
),
|
||||
child: ListTile(
|
||||
leading: RichText(
|
||||
text: TextSpan(
|
||||
text: const TextSpan(
|
||||
text: "-:--",
|
||||
style: TextStyle(fontFamily: "Eurostile Round", fontSize: 22, fontWeight: FontWeight.w500, color: Colors.grey),
|
||||
children: [TextSpan(text: ".---", style: TextStyle(fontFamily: "Eurostile Round", fontSize: 14, fontWeight: FontWeight.w100))]
|
||||
),
|
||||
),
|
||||
title: Text("---", style: TextStyle(color: Colors.grey), textAlign: TextAlign.center),
|
||||
title: const Text("---", style: TextStyle(color: Colors.grey), textAlign: TextAlign.center),
|
||||
trailing: TrailingStats(
|
||||
widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).secondaryTracking[index],
|
||||
widget.record.endContext.firstWhere((element) => element.userId == widget.initPlayerId).tertiaryTracking[index],
|
||||
|
@ -656,7 +685,7 @@ class TlMatchResultState extends State<TlMatchResultView> {
|
|||
if (viewportWidth <= 1024) {
|
||||
return Center(
|
||||
child: Container(
|
||||
constraints: BoxConstraints(maxWidth: 768),
|
||||
constraints: const BoxConstraints(maxWidth: 768),
|
||||
child: buildComparison(viewportWidth > 768, true)
|
||||
),
|
||||
);
|
||||
|
@ -670,7 +699,7 @@ class TlMatchResultState extends State<TlMatchResultView> {
|
|||
child: buildComparison(true, false)
|
||||
),
|
||||
Container(
|
||||
constraints: BoxConstraints(maxWidth: 768),
|
||||
constraints: const BoxConstraints(maxWidth: 768),
|
||||
child: buildRoundSelector(max(viewportWidth-768-16, 200)),
|
||||
)
|
||||
],
|
||||
|
|
|
@ -17,6 +17,7 @@ class GaugetNum extends StatelessWidget {
|
|||
final String? alertTitle;
|
||||
final List<Widget>? alertWidgets;
|
||||
final LeaderboardPosition? pos;
|
||||
final num? averageStat;
|
||||
|
||||
const GaugetNum(
|
||||
{super.key,
|
||||
|
@ -28,7 +29,17 @@ class GaugetNum extends StatelessWidget {
|
|||
required this.minimum,
|
||||
required this.maximum,
|
||||
required this.ranges,
|
||||
this.okText, this.alertTitle, this.pos});
|
||||
this.okText, this.alertTitle, this.pos, this.averageStat});
|
||||
|
||||
Color getStatColor(){
|
||||
if (averageStat == null) return Colors.white;
|
||||
num percentile = (higherIsBetter ? playerStat / averageStat! : averageStat! / playerStat).abs();
|
||||
if (percentile > 1.50) return Colors.purpleAccent;
|
||||
else if (percentile > 1.20) return Colors.blueAccent;
|
||||
else if (percentile > 0.90) return Colors.greenAccent;
|
||||
else if (percentile > 0.70) return Colors.yellowAccent;
|
||||
else return Colors.redAccent;
|
||||
}
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
|
@ -59,7 +70,7 @@ class GaugetNum extends StatelessWidget {
|
|||
],
|
||||
annotations: [GaugeAnnotation(
|
||||
widget: TextButton(child: Text(f3.format(playerStat),
|
||||
style: const TextStyle(fontFamily: "Eurostile Round Extended", fontSize: 36, color: Colors.white)),
|
||||
style: TextStyle(fontFamily: "Eurostile Round Extended", fontSize: 36, color: getStatColor())),
|
||||
onPressed: (){
|
||||
showDialog(
|
||||
context: context,
|
||||
|
|
|
@ -197,7 +197,8 @@ class _TLThingyState extends State<TLThingy> {
|
|||
], alertWidgets: [
|
||||
Text(t.statCellNum.appDescription),
|
||||
Text("${t.exactValue}: ${currentTl.nerdStats!.app}")
|
||||
], oldPlayerStat: oldTl?.nerdStats?.app, pos: widget.lbPositions?.app),
|
||||
], oldPlayerStat: oldTl?.nerdStats?.app, pos: widget.lbPositions?.app,
|
||||
averageStat: rankAverages?.nerdStats?.app),
|
||||
GaugetNum(playerStat: currentTl.nerdStats!.vsapm, playerStatLabel: "VS / APM", higherIsBetter: true, minimum: 1.8, maximum: 2.4, ranges: [
|
||||
GaugeRange(startValue: 1.8, endValue: 2.0, color: Colors.green),
|
||||
GaugeRange(startValue: 2.0, endValue: 2.2, color: Colors.blue),
|
||||
|
@ -205,7 +206,8 @@ class _TLThingyState extends State<TLThingy> {
|
|||
], alertWidgets: [
|
||||
Text(t.statCellNum.vsapmDescription),
|
||||
Text("${t.exactValue}: ${currentTl.nerdStats!.vsapm}")
|
||||
], oldPlayerStat: oldTl?.nerdStats?.vsapm, pos: widget.lbPositions?.vsapm)
|
||||
], oldPlayerStat: oldTl?.nerdStats?.vsapm, pos: widget.lbPositions?.vsapm,
|
||||
averageStat: rankAverages?.nerdStats?.vsapm)
|
||||
]),
|
||||
),
|
||||
Wrap(
|
||||
|
@ -244,7 +246,7 @@ class _TLThingyState extends State<TLThingy> {
|
|||
oldPlayerStat: oldTl?.nerdStats?.appdsp,),
|
||||
StatCellNum(playerStat: currentTl.nerdStats!.cheese, isScreenBig: bigScreen, fractionDigits: 2, playerStatLabel: t.statCellNum.cheese,
|
||||
pos: widget.lbPositions?.cheese,
|
||||
averageStat: rankAverages?.nerdStats?.cheese,
|
||||
//averageStat: rankAverages?.nerdStats?.cheese, TODO: questonable
|
||||
alertWidgets: [Text(t.statCellNum.cheeseDescription),
|
||||
Text("${t.formula}: (DS/P * 150) + ((VS/APM - 2) * 50) + (0.6 - APP) * 125"),
|
||||
Text("${t.exactValue}: ${currentTl.nerdStats!.cheese}"),],
|
||||
|
|
Loading…
Reference in New Issue