/* Copyright (C) 2017 João Paulo Barraca This file is part of Gadgetbridge. Gadgetbridge is free software: you can redistribute it and/or modify it under the terms of the GNU Affero General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. Gadgetbridge is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for more details. You should have received a copy of the GNU Affero General Public License along with this program. If not, see . */ package nodomain.freeyourgadget.gadgetbridge.service.devices.hplus; /* * @author João Paulo Barraca <jpbarraca@gmail.com> */ import java.util.GregorianCalendar; import java.util.Locale; import nodomain.freeyourgadget.gadgetbridge.model.ActivityAmount; import nodomain.freeyourgadget.gadgetbridge.model.ActivityKind; import nodomain.freeyourgadget.gadgetbridge.model.ActivitySample; class HPlusDataRecordRealtime extends HPlusDataRecord { /** * Distance accumulated during the day in meters */ public int distance; /** * Calories consumed during the day in KCalories */ public int calories; /** * Instantaneous Heart Rate measured in Beats Per Minute */ public int heartRate; /** * Battery level from 0 to 100 */ public byte battery; /** * Number of steps today */ public int steps; /** * Time active (To be determined how it works) */ public int activeTime; /** * Computing intensity * To be calculated appropriately */ public int intensity; public HPlusDataRecordRealtime(byte[] data, int age) { super(data, TYPE_REALTIME); if (data.length < 15) { throw new IllegalArgumentException("Invalid data packet"); } timestamp = (int) (GregorianCalendar.getInstance().getTimeInMillis() / 1000); distance = 10 * ((data[4] & 0xFF) * 256 + (data[3] & 0xFF)); // meters steps = (data[2] & 0xFF) * 256 + (data[1] & 0xFF); int x = (data[6] & 0xFF) * 256 + (data[5] & 0xFF); int y = (data[8] & 0xFF) * 256 + (data[7] & 0xFF); battery = data[9]; calories = x + y; // KCal activeTime = (data[14] & 0xFF * 256) + (data[13] & 0xFF); if (battery == 255) { battery = ActivitySample.NOT_MEASURED; heartRate = ActivitySample.NOT_MEASURED; intensity = 0; activityKind = ActivityKind.TYPE_NOT_WORN; } else { heartRate = data[11] & 0xFF; // BPM if (heartRate == 255) { intensity = 0; activityKind = ActivityKind.TYPE_NOT_MEASURED; heartRate = ActivitySample.NOT_MEASURED; } else { intensity = (int) ((100 * heartRate) / (208 - 0.7 * age)); activityKind = HPlusDataRecord.TYPE_REALTIME; } } } public void computeActivity(HPlusDataRecordRealtime prev){ if(prev == null) return; int deltaDistance = distance - prev.distance; if(deltaDistance <= 0) return; int deltaTime = timestamp - prev.timestamp; if(deltaTime <= 0) return; double speed = deltaDistance / deltaTime; if(speed >= 1.6) // ~6 KM/h activityKind = ActivityKind.TYPE_ACTIVITY; } public boolean same(HPlusDataRecordRealtime other){ if(other == null) return false; return steps == other.steps && distance == other.distance && calories == other.calories && heartRate == other.heartRate && battery == other.battery; } public String toString(){ return String.format(Locale.US, "Distance: %d Steps: %d Calories: %d HeartRate: %d Battery: %d ActiveTime: %d Intensity: %d", distance, steps, calories, heartRate, battery, activeTime, intensity); } }