1
0
mirror of https://codeberg.org/Freeyourgadget/Gadgetbridge synced 2025-01-13 03:07:32 +01:00

Huawei Workout cleanup of unknown values

This commit is contained in:
Martin.JM 2024-03-19 14:28:03 +01:00
parent 7a752381cc
commit e8ddc1fd17
2 changed files with 250 additions and 128 deletions

View File

@ -264,7 +264,7 @@ public class Workout {
} }
} }
// TODO: I'm not sure about the lengths // I'm not sure about the lengths, but we haven't gotten any complaints so they probably are fine
private final byte[] bitmapLengths = {1, 2, 1, 2, 2, 4, -1, 2, 2, 1, 1, 1, 1, 1, 1, 1}; private final byte[] bitmapLengths = {1, 2, 1, 2, 2, 4, -1, 2, 2, 1, 1, 1, 1, 1, 1, 1};
private final byte[] innerBitmapLengths = {2, 2, 2, 1, 2, 1, 1, 1, 1, 2, 2, 1, 1, 1, 1, 1}; private final byte[] innerBitmapLengths = {2, 2, 2, 1, 2, 1, 1, 1, 1, 2, 2, 1, 1, 1, 1, 1};

View File

@ -24,13 +24,11 @@ import org.slf4j.LoggerFactory;
import java.nio.charset.StandardCharsets; import java.nio.charset.StandardCharsets;
import java.util.Date; import java.util.Date;
import java.util.Iterator;
import java.util.List; import java.util.List;
import java.util.ListIterator; import java.util.ListIterator;
import de.greenrobot.dao.query.QueryBuilder; import de.greenrobot.dao.query.QueryBuilder;
import nodomain.freeyourgadget.gadgetbridge.GBApplication; import nodomain.freeyourgadget.gadgetbridge.GBApplication;
import nodomain.freeyourgadget.gadgetbridge.GBException;
import nodomain.freeyourgadget.gadgetbridge.database.DBHandler; import nodomain.freeyourgadget.gadgetbridge.database.DBHandler;
import nodomain.freeyourgadget.gadgetbridge.devices.huawei.packets.Workout; import nodomain.freeyourgadget.gadgetbridge.devices.huawei.packets.Workout;
import nodomain.freeyourgadget.gadgetbridge.entities.BaseActivitySummary; import nodomain.freeyourgadget.gadgetbridge.entities.BaseActivitySummary;
@ -42,7 +40,6 @@ import nodomain.freeyourgadget.gadgetbridge.entities.HuaweiWorkoutPaceSampleDao;
import nodomain.freeyourgadget.gadgetbridge.entities.HuaweiWorkoutSummarySample; import nodomain.freeyourgadget.gadgetbridge.entities.HuaweiWorkoutSummarySample;
import nodomain.freeyourgadget.gadgetbridge.entities.HuaweiWorkoutSummarySampleDao; import nodomain.freeyourgadget.gadgetbridge.entities.HuaweiWorkoutSummarySampleDao;
import nodomain.freeyourgadget.gadgetbridge.model.ActivityKind; import nodomain.freeyourgadget.gadgetbridge.model.ActivityKind;
import nodomain.freeyourgadget.gadgetbridge.service.devices.sonyswr12.entities.activity.ActivityType;
import nodomain.freeyourgadget.gadgetbridge.util.GB; import nodomain.freeyourgadget.gadgetbridge.util.GB;
import nodomain.freeyourgadget.gadgetbridge.util.StringUtils; import nodomain.freeyourgadget.gadgetbridge.util.StringUtils;
@ -232,177 +229,302 @@ public class HuaweiWorkoutGbParser {
typeJson.put("unit", ""); typeJson.put("unit", "");
jsonObject.put("Type", typeJson); jsonObject.put("Type", typeJson);
JSONObject strokesJson = new JSONObject(); if (summary.getStrokes() != -1) {
strokesJson.put("value", summary.getStrokes()); JSONObject strokesJson = new JSONObject();
strokesJson.put("unit", ""); strokesJson.put("value", summary.getStrokes());
jsonObject.put("Strokes", strokesJson); strokesJson.put("unit", "");
jsonObject.put("Strokes", strokesJson);
}
JSONObject avgStrokeRateJson = new JSONObject(); if (summary.getAvgStrokeRate() != -1) {
avgStrokeRateJson.put("value", summary.getAvgStrokeRate()); JSONObject avgStrokeRateJson = new JSONObject();
avgStrokeRateJson.put("unit", ""); avgStrokeRateJson.put("value", summary.getAvgStrokeRate());
jsonObject.put("Average reported stroke rate", avgStrokeRateJson); avgStrokeRateJson.put("unit", "");
jsonObject.put("Average reported stroke rate", avgStrokeRateJson);
}
JSONObject poolLengthJson = new JSONObject(); if (summary.getPoolLength() != -1) {
poolLengthJson.put("value", summary.getPoolLength()); JSONObject poolLengthJson = new JSONObject();
poolLengthJson.put("unit", "cm"); poolLengthJson.put("value", summary.getPoolLength());
jsonObject.put("Pool length", poolLengthJson); poolLengthJson.put("unit", "cm");
jsonObject.put("Pool length", poolLengthJson);
}
JSONObject lapsJson = new JSONObject(); if (summary.getLaps() != -1) {
lapsJson.put("value", summary.getLaps()); JSONObject lapsJson = new JSONObject();
lapsJson.put("unit", ""); lapsJson.put("value", summary.getLaps());
jsonObject.put("Laps", lapsJson); lapsJson.put("unit", "");
jsonObject.put("Laps", lapsJson);
}
JSONObject avgSwolfJson = new JSONObject(); if (summary.getAvgSwolf() != -1) {
avgSwolfJson.put("value", summary.getAvgSwolf()); JSONObject avgSwolfJson = new JSONObject();
avgSwolfJson.put("unit", ""); avgSwolfJson.put("value", summary.getAvgSwolf());
jsonObject.put("Average reported swolf", avgSwolfJson); avgSwolfJson.put("unit", "");
jsonObject.put("Average reported swolf", avgSwolfJson);
}
boolean unknownData = false; boolean unknownData = false;
if (dataSamples.size() != 0) { if (dataSamples.size() != 0) {
int speed = 0; int speed = 0;
int speedCount = 0;
boolean stepRatePresent = false;
int stepRate = 0; int stepRate = 0;
int avgStepRate = 0;
int cadence = 0; int cadence = 0;
int cadenceCount = 0;
int stepLength = 0; int stepLength = 0;
int stepLengthCount = 0;
int groundContactTime = 0; int groundContactTime = 0;
int groundContactTimeCount = 0;
int impact = 0; int impact = 0;
int impactCount = 0;
int maxImpact = 0; int maxImpact = 0;
int swingAngle = 0; int swingAngle = 0;
int swingAngleCount = 0;
boolean footLandingPresent = false;
int foreFootLanding = 0; int foreFootLanding = 0;
int midFootLanding = 0; int midFootLanding = 0;
int backFootLanding = 0; int backFootLanding = 0;
int eversionAngle = 0; int eversionAngle = 0;
int eversionAngleCount = 0;
int maxEversionAngle = 0; int maxEversionAngle = 0;
int swolf = 0; int swolf = 0;
int swolfCount = 0;
int maxSwolf = 0; int maxSwolf = 0;
int strokeRate = 0; int strokeRate = 0;
int strokeRateCount = 0;
int maxStrokeRate = 0; int maxStrokeRate = 0;
int heartRate = 0;
int heartRateCount = 0;
int maxHeartRate = 0;
int minHeartRate = Integer.MAX_VALUE;
for (HuaweiWorkoutDataSample dataSample : dataSamples) { for (HuaweiWorkoutDataSample dataSample : dataSamples) {
speed += dataSample.getSpeed(); if (dataSample.getSpeed() != -1) {
stepRate += dataSample.getStepRate(); speed += dataSample.getSpeed();
cadence += dataSample.getCadence(); speedCount += 1;
stepLength += dataSample.getStepLength(); }
groundContactTime += dataSample.getGroundContactTime(); if (dataSample.getStepRate() != -1) {
impact += dataSample.getImpact(); stepRate += dataSample.getStepRate();
if (dataSample.getImpact() > maxImpact) stepRatePresent = true;
maxImpact = dataSample.getImpact(); }
swingAngle += dataSample.getSwingAngle(); if (dataSample.getCadence() != -1) {
foreFootLanding += dataSample.getForeFootLanding(); cadence += dataSample.getCadence();
midFootLanding += dataSample.getMidFootLanding(); cadenceCount += 1;
backFootLanding += dataSample.getBackFootLanding(); }
eversionAngle += dataSample.getEversionAngle(); if (dataSample.getStepLength() != -1) {
if (dataSample.getEversionAngle() > maxEversionAngle) stepLength += dataSample.getStepLength();
maxEversionAngle = dataSample.getEversionAngle(); stepLengthCount += 1;
swolf += dataSample.getSwolf(); }
if (dataSample.getSwolf() > maxSwolf) if (dataSample.getGroundContactTime() != -1) {
maxSwolf = dataSample.getSwolf(); groundContactTime += dataSample.getGroundContactTime();
strokeRate += dataSample.getStrokeRate(); groundContactTimeCount += 1;
if (dataSample.getStrokeRate() > maxStrokeRate) }
maxStrokeRate = dataSample.getStrokeRate(); if (dataSample.getImpact() != -1) {
impact += dataSample.getImpact();
impactCount += 1;
if (dataSample.getImpact() > maxImpact)
maxImpact = dataSample.getImpact();
}
if (dataSample.getSwingAngle() != -1) {
swingAngle += dataSample.getSwingAngle();
swingAngleCount += 1;
}
if (dataSample.getForeFootLanding() != -1) {
foreFootLanding += dataSample.getForeFootLanding();
footLandingPresent = true;
}
if (dataSample.getMidFootLanding() != -1) {
midFootLanding += dataSample.getMidFootLanding();
footLandingPresent = true;
}
if (dataSample.getBackFootLanding() != -1) {
backFootLanding += dataSample.getBackFootLanding();
footLandingPresent = true;
}
if (dataSample.getEversionAngle() != -1) {
eversionAngle += dataSample.getEversionAngle();
eversionAngleCount += 1;
if (dataSample.getEversionAngle() > maxEversionAngle)
maxEversionAngle = dataSample.getEversionAngle();
}
if (dataSample.getSwolf() != -1) {
swolf += dataSample.getSwolf();
swolfCount += 1;
if (dataSample.getSwolf() > maxSwolf)
maxSwolf = dataSample.getSwolf();
}
if (dataSample.getStrokeRate() != -1) {
strokeRate += dataSample.getStrokeRate();
strokeRateCount += 1;
if (dataSample.getStrokeRate() > maxStrokeRate)
maxStrokeRate = dataSample.getStrokeRate();
}
if (dataSample.getHeartRate() != -1 && dataSample.getHeartRate() != 0) {
int hr = dataSample.getHeartRate() & 0xff;
heartRate += hr;
heartRateCount += 1;
if (hr > maxHeartRate)
maxHeartRate = hr;
if (hr < minHeartRate)
minHeartRate = hr;
}
if (dataSample.getDataErrorHex() != null) if (dataSample.getDataErrorHex() != null)
unknownData = true; unknownData = true;
} }
// Average the things that should probably be averaged
speed = speed / dataSamples.size();
cadence = cadence / dataSamples.size();
int avgStepRate = stepRate / (summary.getDuration() / 60); // steps per minute
stepLength = stepLength / dataSamples.size(); // Average the things that should be averaged
groundContactTime = groundContactTime / dataSamples.size(); if (speedCount > 0)
impact = impact / dataSamples.size(); speed = speed / speedCount;
swingAngle = swingAngle / dataSamples.size(); if (cadenceCount > 0)
eversionAngle = eversionAngle / dataSamples.size(); cadence = cadence / cadenceCount;
swolf = swolf / dataSamples.size(); if (summary.getDuration() > 60)
strokeRate = strokeRate / dataSamples.size(); avgStepRate = stepRate / (summary.getDuration() / 60); // steps per minute
if (stepLengthCount > 0)
stepLength = stepLength / stepLengthCount;
if (groundContactTimeCount > 0)
groundContactTime = groundContactTime / groundContactTimeCount;
if (impactCount > 0)
impact = impact / impactCount;
if (swingAngleCount > 0)
swingAngle = swingAngle / swingAngleCount;
if (eversionAngleCount > 0)
eversionAngle = eversionAngle / eversionAngleCount;
if (swolfCount > 0)
swolf = swolf / swolfCount;
if (strokeRateCount > 0)
strokeRate = strokeRate / strokeRateCount;
if (heartRateCount > 0)
heartRate = heartRate / heartRateCount;
JSONObject speedJson = new JSONObject(); if (speedCount > 0) {
speedJson.put("value", speed); JSONObject speedJson = new JSONObject();
speedJson.put("unit", "cm/s"); speedJson.put("value", speed);
jsonObject.put("Reported speed (avg)", speedJson); speedJson.put("unit", "cm/s");
jsonObject.put("Reported speed (avg)", speedJson);
}
JSONObject stepRateSumJson = new JSONObject(); if (stepRatePresent) {
stepRateSumJson.put("value", stepRate); JSONObject stepRateSumJson = new JSONObject();
stepRateSumJson.put("unit", ""); stepRateSumJson.put("value", stepRate);
jsonObject.put("Step rate (sum)", stepRateSumJson); stepRateSumJson.put("unit", "");
jsonObject.put("Step rate (sum)", stepRateSumJson);
JSONObject stepRateAvgJson = new JSONObject(); JSONObject stepRateAvgJson = new JSONObject();
stepRateAvgJson.put("value", avgStepRate); stepRateAvgJson.put("value", avgStepRate);
stepRateAvgJson.put("unit", "steps/min"); stepRateAvgJson.put("unit", "steps/min");
jsonObject.put("Step rate (avg)", stepRateAvgJson); jsonObject.put("Step rate (avg)", stepRateAvgJson);
}
JSONObject cadenceJson = new JSONObject(); if (cadenceCount > 0) {
cadenceJson.put("value", cadence); JSONObject cadenceJson = new JSONObject();
cadenceJson.put("unit", "steps/min"); cadenceJson.put("value", cadence);
jsonObject.put("Cadence (avg)", cadenceJson); cadenceJson.put("unit", "steps/min");
jsonObject.put("Cadence (avg)", cadenceJson);
}
JSONObject stepLengthJson = new JSONObject(); if (stepLengthCount > 0) {
stepLengthJson.put("value", stepLength); JSONObject stepLengthJson = new JSONObject();
stepLengthJson.put("unit", "cm"); stepLengthJson.put("value", stepLength);
jsonObject.put("Step Length (avg)", stepLengthJson); stepLengthJson.put("unit", "cm");
jsonObject.put("Step Length (avg)", stepLengthJson);
}
JSONObject groundContactTimeJson = new JSONObject(); if (groundContactTimeCount > 0) {
groundContactTimeJson.put("value", groundContactTime); JSONObject groundContactTimeJson = new JSONObject();
groundContactTimeJson.put("unit", "milliseconds"); groundContactTimeJson.put("value", groundContactTime);
jsonObject.put("Ground contact time (avg)", groundContactTimeJson); groundContactTimeJson.put("unit", "milliseconds");
jsonObject.put("Ground contact time (avg)", groundContactTimeJson);
}
JSONObject impactJson = new JSONObject(); if (impactCount > 0) {
impactJson.put("value", impact); JSONObject impactJson = new JSONObject();
impactJson.put("unit", "g"); impactJson.put("value", impact);
jsonObject.put("Impact (avg)", impactJson); impactJson.put("unit", "g");
jsonObject.put("Impact (avg)", impactJson);
JSONObject maxImpactJson = new JSONObject(); JSONObject maxImpactJson = new JSONObject();
maxImpactJson.put("value", maxImpact); maxImpactJson.put("value", maxImpact);
maxImpactJson.put("unit", "g"); maxImpactJson.put("unit", "g");
jsonObject.put("Impact (max)", maxImpactJson); jsonObject.put("Impact (max)", maxImpactJson);
}
JSONObject swingAngleJson = new JSONObject(); if (swingAngleCount > 0) {
swingAngleJson.put("value", swingAngle); JSONObject swingAngleJson = new JSONObject();
swingAngleJson.put("unit", "degrees"); swingAngleJson.put("value", swingAngle);
jsonObject.put("Swing angle (avg)", swingAngleJson); swingAngleJson.put("unit", "degrees");
jsonObject.put("Swing angle (avg)", swingAngleJson);
}
JSONObject foreFootLandingJson = new JSONObject(); if (footLandingPresent) {
foreFootLandingJson.put("value", foreFootLanding); JSONObject foreFootLandingJson = new JSONObject();
foreFootLandingJson.put("unit", ""); foreFootLandingJson.put("value", foreFootLanding);
jsonObject.put("Fore foot landings", foreFootLandingJson); foreFootLandingJson.put("unit", "");
jsonObject.put("Fore foot landings", foreFootLandingJson);
JSONObject midFootLandingJson = new JSONObject(); JSONObject midFootLandingJson = new JSONObject();
midFootLandingJson.put("value", midFootLanding); midFootLandingJson.put("value", midFootLanding);
midFootLandingJson.put("unit", ""); midFootLandingJson.put("unit", "");
jsonObject.put("Mid foot landings", midFootLandingJson); jsonObject.put("Mid foot landings", midFootLandingJson);
JSONObject backFootLandingJson = new JSONObject(); JSONObject backFootLandingJson = new JSONObject();
backFootLandingJson.put("value", backFootLanding); backFootLandingJson.put("value", backFootLanding);
backFootLandingJson.put("unit", ""); backFootLandingJson.put("unit", "");
jsonObject.put("Back foot landings", backFootLandingJson); jsonObject.put("Back foot landings", backFootLandingJson);
}
JSONObject eversionAngleJson = new JSONObject(); if (eversionAngleCount > 0) {
eversionAngleJson.put("value", eversionAngle); JSONObject eversionAngleJson = new JSONObject();
eversionAngleJson.put("unit", "degrees"); eversionAngleJson.put("value", eversionAngle);
jsonObject.put("Eversion angle (avg)", eversionAngleJson); eversionAngleJson.put("unit", "degrees");
jsonObject.put("Eversion angle (avg)", eversionAngleJson);
JSONObject maxEversionAngleJson = new JSONObject(); JSONObject maxEversionAngleJson = new JSONObject();
maxEversionAngleJson.put("value", maxEversionAngle); maxEversionAngleJson.put("value", maxEversionAngle);
maxEversionAngleJson.put("unit", "degrees"); maxEversionAngleJson.put("unit", "degrees");
jsonObject.put("Eversion angle (max)", maxEversionAngleJson); jsonObject.put("Eversion angle (max)", maxEversionAngleJson);
}
JSONObject swolfJson = new JSONObject(); if (swolfCount > 0) {
swolfJson.put("value", swolf); JSONObject swolfJson = new JSONObject();
swolfJson.put("unit", ""); swolfJson.put("value", swolf);
jsonObject.put("Swolf (avg calculated)", swolfJson); swolfJson.put("unit", "");
jsonObject.put("Swolf (avg calculated)", swolfJson);
JSONObject maxSwolfJson = new JSONObject(); JSONObject maxSwolfJson = new JSONObject();
maxSwolfJson.put("value", maxSwolf); maxSwolfJson.put("value", maxSwolf);
maxSwolfJson.put("unit", ""); maxSwolfJson.put("unit", "");
jsonObject.put("Swolf (max)", maxSwolfJson); jsonObject.put("Swolf (max)", maxSwolfJson);
}
JSONObject strokeRateJson = new JSONObject(); if (strokeRateCount > 0) {
strokeRateJson.put("value", strokeRate); JSONObject strokeRateJson = new JSONObject();
strokeRateJson.put("unit", ""); strokeRateJson.put("value", strokeRate);
jsonObject.put("Stroke rate (avg calculated)", strokeRateJson); strokeRateJson.put("unit", "");
jsonObject.put("Stroke rate (avg calculated)", strokeRateJson);
JSONObject maxStrokeRateJson = new JSONObject(); JSONObject maxStrokeRateJson = new JSONObject();
maxStrokeRateJson.put("value", maxStrokeRate); maxStrokeRateJson.put("value", maxStrokeRate);
maxStrokeRateJson.put("unit", ""); maxStrokeRateJson.put("unit", "");
jsonObject.put("Stroke rate (max)", maxStrokeRateJson); jsonObject.put("Stroke rate (max)", maxStrokeRateJson);
}
if (heartRateCount > 0) {
JSONObject heartRateJson = new JSONObject();
heartRateJson.put("value", heartRate);
heartRateJson.put("unit", "bpm");
jsonObject.put("Heart rate (avg)", heartRateJson);
JSONObject maxHeartRateJson = new JSONObject();
maxHeartRateJson.put("value", maxHeartRate);
maxHeartRateJson.put("unit", "bpm");
jsonObject.put("Heart rate (max)", maxHeartRateJson);
JSONObject minHeartRateJson = new JSONObject();
minHeartRateJson.put("value", minHeartRate);
minHeartRateJson.put("unit", "bpm");
jsonObject.put("Heart rate (min)", minHeartRateJson);
}
} }
ListIterator<HuaweiWorkoutPaceSample> it = qbPace.build().listIterator(); ListIterator<HuaweiWorkoutPaceSample> it = qbPace.build().listIterator();