244 lines
8.0 KiB
Dart
244 lines
8.0 KiB
Dart
import 'package:aitrainer_app/model/result.dart';
|
|
import 'package:aitrainer_app/repository/evaluation_repository.dart';
|
|
import 'package:aitrainer_app/repository/exercise_repository.dart';
|
|
import 'package:aitrainer_app/repository/exercise_result_repository.dart';
|
|
import 'package:aitrainer_app/service/logging.dart';
|
|
import 'package:aitrainer_app/util/trans.dart';
|
|
import 'package:bloc/bloc.dart';
|
|
import 'package:equatable/equatable.dart';
|
|
import 'package:flutter/material.dart';
|
|
|
|
//import 'package:health/health.dart';
|
|
|
|
part 'result_event.dart';
|
|
part 'result_state.dart';
|
|
|
|
class ResultBloc extends Bloc<ResultEvent, ResultState> with Logging, Trans {
|
|
final ExerciseResultRepository resultRepository;
|
|
final ExerciseRepository exerciseRepository;
|
|
final EvaluationRepository evaluationRepository = EvaluationRepository();
|
|
final BuildContext context;
|
|
//List<HealthDataPoint> _healthDataList = [];
|
|
DateTime? startTime;
|
|
DateTime? endTime;
|
|
/* final HealthFactory health = HealthFactory();
|
|
final List<HealthDataType> types = [
|
|
HealthDataType.ACTIVE_ENERGY_BURNED,
|
|
HealthDataType.WATER,
|
|
HealthDataType.STEPS,
|
|
HealthDataType.HEART_RATE,
|
|
HealthDataType.BASAL_ENERGY_BURNED,
|
|
HealthDataType.BODY_TEMPERATURE,
|
|
HealthDataType.HIGH_HEART_RATE_EVENT,
|
|
HealthDataType.LOW_HEART_RATE_EVENT,
|
|
HealthDataType.RESTING_HEART_RATE
|
|
]; */
|
|
|
|
ResultBloc({required this.resultRepository, required this.exerciseRepository, required this.context}) : super(ResultInitial()) {
|
|
this._load();
|
|
on<ResultLoad>(_onLoad);
|
|
}
|
|
|
|
void _load() {
|
|
this.startTime = exerciseRepository.start;
|
|
this.endTime = exerciseRepository.end;
|
|
if (this.startTime == null) {
|
|
this.startTime = exerciseRepository.exercise!.dateAdd!;
|
|
exerciseRepository.start = exerciseRepository.exercise!.dateAdd!;
|
|
}
|
|
}
|
|
|
|
void _onLoad(ResultLoad event, Emitter<ResultState> emit) {
|
|
emit(ResultLoading());
|
|
_matchExerciseData();
|
|
emit(ResultReady());
|
|
}
|
|
|
|
void _matchExerciseData() {
|
|
resultRepository.getResults().forEach((element) {
|
|
element.dateFrom = startTime;
|
|
element.dateTo = endTime;
|
|
element.exerciseId = exerciseRepository.actualExerciseList![0].exerciseId;
|
|
switch (element.item) {
|
|
case ResultItem.bpm_avg:
|
|
//element.data = _gethHealthDataPointValueAvg(HealthDataType.HEART_RATE);
|
|
break;
|
|
case ResultItem.bpm_min:
|
|
//element.data = element.data = _gethHealthDataPointValueMin(HealthDataType.HEART_RATE);
|
|
break;
|
|
case ResultItem.bpm_max:
|
|
//element.data = element.data = _gethHealthDataPointValueMax(HealthDataType.HEART_RATE);
|
|
break;
|
|
case ResultItem.calorie:
|
|
//element.data = _gethHealthDataPointValueSum(HealthDataType.ACTIVE_ENERGY_BURNED);
|
|
break;
|
|
case ResultItem.development_percent_bodypart:
|
|
break;
|
|
case ResultItem.distance:
|
|
if (exerciseRepository.exerciseType!.unit == "meter") {
|
|
element.data = exerciseRepository.exercise!.quantity!;
|
|
}
|
|
break;
|
|
case ResultItem.fatburn_percent:
|
|
/* DateTime today = DateTime.now();
|
|
int age = today.year - Cache().userLoggedIn.birthYear;
|
|
double minBpm = (200 - age) * 0.6;
|
|
double maxBpm = (200 - age) * 0.7;
|
|
int counter = 0;
|
|
int burnCounter = 0;
|
|
_healthDataList.forEach((dataPoint) {
|
|
if (dataPoint.type == HealthDataType.ACTIVE_ENERGY_BURNED) {
|
|
if (dataPoint.value >= minBpm && dataPoint.value <= maxBpm) {
|
|
burnCounter++;
|
|
}
|
|
counter++;
|
|
}
|
|
});
|
|
if (counter > 0) {
|
|
element.data = (burnCounter / counter * 100);
|
|
} else {
|
|
element.data = 0;
|
|
} */
|
|
break;
|
|
case ResultItem.speed_max:
|
|
break;
|
|
case ResultItem.reps_volume:
|
|
if (exerciseRepository.exerciseType!.unit == "repeat") {
|
|
double value = 0;
|
|
exerciseRepository.actualExerciseList!.forEach((actual) {
|
|
value += actual.quantity!;
|
|
});
|
|
element.data = value;
|
|
}
|
|
break;
|
|
case ResultItem.steps:
|
|
element.data = 0; //_gethHealthDataPointValueSum(HealthDataType.STEPS);
|
|
break;
|
|
/* case ResultItem.time:
|
|
final Duration duration = this.endTime.difference(this.startTime);
|
|
element.data = _printDuration(duration);
|
|
break; */
|
|
case ResultItem.weight_volume:
|
|
if (exerciseRepository.exerciseType!.unitQuantityUnit == "kilogram") {
|
|
double value = 0;
|
|
exerciseRepository.actualExerciseList!.forEach((actual) {
|
|
value += actual.quantity! * actual.unitQuantity!;
|
|
});
|
|
element.data = value;
|
|
}
|
|
break;
|
|
}
|
|
});
|
|
}
|
|
|
|
String printDuration(Duration duration, {isText = false, isDecimal = false}) {
|
|
String twoDigits(int n) => n.toString().padLeft(2, "0");
|
|
String twoDigitMinutes = twoDigits(duration.inMinutes);
|
|
String twoDigitSeconds = twoDigits(duration.inSeconds.remainder(60));
|
|
String twoDigitMilliSeconds = duration.inMilliseconds.remainder(1000).toString();
|
|
if (isText) {
|
|
if (isDecimal) {
|
|
return "$twoDigitMinutes" + t("min") + "$twoDigitSeconds" + t("sec") + ":$twoDigitMilliSeconds" + '"';
|
|
} else {
|
|
return "$twoDigitMinutes" + t("min") + "$twoDigitSeconds" + t("sec");
|
|
}
|
|
} else {
|
|
return "$twoDigitMinutes:$twoDigitSeconds:$twoDigitMilliSeconds" + '"';
|
|
}
|
|
}
|
|
|
|
String printTime(double duration) {
|
|
String twoDigits(int n) => n.toString().padLeft(1, "0");
|
|
String twoDigitMinutes = twoDigits((duration ~/ 60).toInt());
|
|
String twoDigitSeconds = (duration % 60).toStringAsFixed(0);
|
|
|
|
return "$twoDigitMinutes " + t("minutes") + " $twoDigitSeconds";
|
|
}
|
|
|
|
/* double _gethHealthDataPointValueAvg(HealthDataType dataType) {
|
|
double value = 0;
|
|
double counter = 0;
|
|
_healthDataList.forEach((dataPoint) {
|
|
if (dataPoint.type == dataType) {
|
|
value += dataPoint.value;
|
|
counter++;
|
|
}
|
|
});
|
|
double avg = 0;
|
|
if (counter > 0) {
|
|
avg = value / counter;
|
|
}
|
|
return avg;
|
|
}
|
|
|
|
double _gethHealthDataPointValueSum(HealthDataType dataType) {
|
|
double value = 0;
|
|
_healthDataList.forEach((dataPoint) {
|
|
if (dataPoint.type == dataType) {
|
|
value += dataPoint.value;
|
|
}
|
|
});
|
|
return value;
|
|
}
|
|
|
|
double _gethHealthDataPointValueMax(HealthDataType dataType) {
|
|
double max = 0;
|
|
_healthDataList.forEach((dataPoint) {
|
|
if (dataPoint.type == dataType) {
|
|
if (max < dataPoint.value) {
|
|
max = dataPoint.value;
|
|
}
|
|
}
|
|
});
|
|
return max;
|
|
}
|
|
|
|
double _gethHealthDataPointValueMin(HealthDataType dataType) {
|
|
double min = 9999999;
|
|
_healthDataList.forEach((dataPoint) {
|
|
if (dataPoint.type == dataType) {
|
|
if (min > dataPoint.value && dataPoint.value != 0) {
|
|
min = dataPoint.value;
|
|
}
|
|
}
|
|
});
|
|
if (min == 9999999) {
|
|
min = 0;
|
|
}
|
|
return min;
|
|
} */
|
|
|
|
/* Future<void> _fetchHealthData() async {
|
|
if (health == null) {
|
|
return;
|
|
}
|
|
try {
|
|
log("Get Health data between " + startTime.toString() + " AND " + endTime.toString());
|
|
_healthDataList = await health.getHealthDataFromTypes(this.startTime, this.endTime, types);
|
|
_healthDataList.forEach((element) {
|
|
log(element.toString());
|
|
});
|
|
} on Exception catch (e) {
|
|
log("Caught exception in getHealthDataFromTypes: $e");
|
|
throw Exception(e);
|
|
}
|
|
} */
|
|
|
|
double calculate1RM({double percent = 0.75}) {
|
|
if (exerciseRepository.exercise == null) {
|
|
exerciseRepository.getLastExercise();
|
|
}
|
|
double weight = exerciseRepository.exercise!.unitQuantity!;
|
|
double repeat = exerciseRepository.exercise!.quantity!;
|
|
if (weight == 0 || repeat == 0) {
|
|
return 0;
|
|
}
|
|
|
|
double rmWendler = weight * repeat * 0.0333 + weight;
|
|
double rmOconner = weight * (1 + repeat / 40);
|
|
double average = (rmWendler + rmOconner) / 2;
|
|
|
|
return average * percent;
|
|
}
|
|
}
|