More WIP on Omnipod Dash program basal command
This commit is contained in:
parent
1c490f72ae
commit
79c9e9a938
5 changed files with 191 additions and 35 deletions
|
@ -8,6 +8,7 @@ import java.util.List;
|
||||||
import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.pod.command.base.CommandType;
|
import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.pod.command.base.CommandType;
|
||||||
import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.pod.command.base.HeaderEnabledCommand;
|
import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.pod.command.base.HeaderEnabledCommand;
|
||||||
import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.pod.command.base.builder.NonceEnabledCommandBuilder;
|
import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.pod.command.base.builder.NonceEnabledCommandBuilder;
|
||||||
|
import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.pod.command.insulin.program.CurrentLongInsulinProgramElement;
|
||||||
import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.pod.command.insulin.program.CurrentSlot;
|
import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.pod.command.insulin.program.CurrentSlot;
|
||||||
import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.pod.command.insulin.program.LongInsulinProgramElement;
|
import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.pod.command.insulin.program.LongInsulinProgramElement;
|
||||||
import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.pod.command.insulin.program.ProgramBasalUtil;
|
import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.pod.command.insulin.program.ProgramBasalUtil;
|
||||||
|
@ -87,9 +88,6 @@ public final class ProgramBasalCommand extends HeaderEnabledCommand {
|
||||||
private Date currentTime;
|
private Date currentTime;
|
||||||
|
|
||||||
public Builder setBasalProgram(BasalProgram basalProgram) {
|
public Builder setBasalProgram(BasalProgram basalProgram) {
|
||||||
if (basalProgram == null) {
|
|
||||||
throw new IllegalArgumentException("basalProgram can not be null");
|
|
||||||
}
|
|
||||||
this.basalProgram = basalProgram;
|
this.basalProgram = basalProgram;
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
@ -120,15 +118,15 @@ public final class ProgramBasalCommand extends HeaderEnabledCommand {
|
||||||
List<LongInsulinProgramElement> longInsulinProgramElements = ProgramBasalUtil.mapPulsesPerSlotToLongInsulinProgramElements(pulsesPerSlot);
|
List<LongInsulinProgramElement> longInsulinProgramElements = ProgramBasalUtil.mapPulsesPerSlotToLongInsulinProgramElements(pulsesPerSlot);
|
||||||
List<ShortInsulinProgramElement> shortInsulinProgramElements = ProgramBasalUtil.mapPulsesPerSlotToShortInsulinProgramElements(pulsesPerSlot);
|
List<ShortInsulinProgramElement> shortInsulinProgramElements = ProgramBasalUtil.mapPulsesPerSlotToShortInsulinProgramElements(pulsesPerSlot);
|
||||||
short checksum = ProgramBasalUtil.createChecksum();
|
short checksum = ProgramBasalUtil.createChecksum();
|
||||||
byte currentInsulinProgramElementIndex = 0; // TODO
|
CurrentLongInsulinProgramElement currentLongInsulinProgramElement = ProgramBasalUtil.calculateCurrentLongInsulinProgramElement(longInsulinProgramElements, currentTime);
|
||||||
short remainingTenthPulsesInCurrentInsulinProgramElement = 0; // TODO
|
|
||||||
int delayUntilNextPulseInUsec = 0; // TODO
|
|
||||||
|
|
||||||
ProgramInsulinCommand interlockCommand = new ProgramInsulinCommand(address, sequenceNumber, multiCommandFlag, nonce,
|
ProgramInsulinCommand interlockCommand = new ProgramInsulinCommand(address, sequenceNumber, multiCommandFlag, nonce,
|
||||||
shortInsulinProgramElements, currentSlot.getIndex(), checksum, (short) (currentSlot.getSecondsRemaining() * 8),
|
shortInsulinProgramElements, currentSlot.getIndex(), checksum, (short) (currentSlot.getEighthSecondsRemaining() * 8),
|
||||||
currentSlot.getPulsesRemaining(), ProgramInsulinCommand.DeliveryType.BASAL);
|
currentSlot.getPulsesRemaining(), ProgramInsulinCommand.DeliveryType.BASAL);
|
||||||
|
|
||||||
return new ProgramBasalCommand(interlockCommand, address, sequenceNumber, multiCommandFlag, longInsulinProgramElements, programReminder, currentInsulinProgramElementIndex, remainingTenthPulsesInCurrentInsulinProgramElement, delayUntilNextPulseInUsec);
|
return new ProgramBasalCommand(interlockCommand, address, sequenceNumber, multiCommandFlag,
|
||||||
|
longInsulinProgramElements, programReminder, currentLongInsulinProgramElement.getIndex(),
|
||||||
|
currentLongInsulinProgramElement.getRemainingTenthPulses(), currentLongInsulinProgramElement.getDelayUntilNextTenthPulseInUsec());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,39 @@
|
||||||
|
package info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.pod.command.insulin.program;
|
||||||
|
|
||||||
|
import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.pod.definition.Encodable;
|
||||||
|
|
||||||
|
public class CurrentLongInsulinProgramElement implements Encodable {
|
||||||
|
private final byte index;
|
||||||
|
private final int delayUntilNextTenthPulseInUsec;
|
||||||
|
private final short remainingTenthPulses;
|
||||||
|
|
||||||
|
public CurrentLongInsulinProgramElement(byte index, int delayUntilNextTenthPulseInUsec, short remainingTenthPulses) {
|
||||||
|
this.index = index;
|
||||||
|
this.delayUntilNextTenthPulseInUsec = delayUntilNextTenthPulseInUsec;
|
||||||
|
this.remainingTenthPulses = remainingTenthPulses;
|
||||||
|
}
|
||||||
|
|
||||||
|
public byte getIndex() {
|
||||||
|
return index;
|
||||||
|
}
|
||||||
|
|
||||||
|
public int getDelayUntilNextTenthPulseInUsec() {
|
||||||
|
return delayUntilNextTenthPulseInUsec;
|
||||||
|
}
|
||||||
|
|
||||||
|
public short getRemainingTenthPulses() {
|
||||||
|
return remainingTenthPulses;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override public String toString() {
|
||||||
|
return "CurrentLongInsulinProgramElement{" +
|
||||||
|
"index=" + index +
|
||||||
|
", delayUntilNextTenthPulseInUsec=" + delayUntilNextTenthPulseInUsec +
|
||||||
|
", remainingTenthPulses=" + remainingTenthPulses +
|
||||||
|
'}';
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override public byte[] getEncoded() {
|
||||||
|
return new byte[0];
|
||||||
|
}
|
||||||
|
}
|
|
@ -1,13 +1,13 @@
|
||||||
package info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.pod.command.insulin.program;
|
package info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.pod.command.insulin.program;
|
||||||
|
|
||||||
public class CurrentSlot {
|
public class CurrentSlot {
|
||||||
private byte index;
|
private final byte index;
|
||||||
private short secondsRemaining;
|
private final short eighthSecondsRemaining;
|
||||||
private short pulsesRemaining;
|
private final short pulsesRemaining;
|
||||||
|
|
||||||
public CurrentSlot(byte index, short secondsRemaining, short pulsesRemaining) {
|
public CurrentSlot(byte index, short eighthSecondsRemaining, short pulsesRemaining) {
|
||||||
this.index = index;
|
this.index = index;
|
||||||
this.secondsRemaining = secondsRemaining;
|
this.eighthSecondsRemaining = eighthSecondsRemaining;
|
||||||
this.pulsesRemaining = pulsesRemaining;
|
this.pulsesRemaining = pulsesRemaining;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -15,8 +15,8 @@ public class CurrentSlot {
|
||||||
return index;
|
return index;
|
||||||
}
|
}
|
||||||
|
|
||||||
public short getSecondsRemaining() {
|
public short getEighthSecondsRemaining() {
|
||||||
return secondsRemaining;
|
return eighthSecondsRemaining;
|
||||||
}
|
}
|
||||||
|
|
||||||
public short getPulsesRemaining() {
|
public short getPulsesRemaining() {
|
||||||
|
@ -26,7 +26,7 @@ public class CurrentSlot {
|
||||||
@Override public String toString() {
|
@Override public String toString() {
|
||||||
return "CurrentSlot{" +
|
return "CurrentSlot{" +
|
||||||
"index=" + index +
|
"index=" + index +
|
||||||
", secondsRemaining=" + secondsRemaining +
|
", eighthSecondsRemaining=" + eighthSecondsRemaining +
|
||||||
", pulsesRemaining=" + pulsesRemaining +
|
", pulsesRemaining=" + pulsesRemaining +
|
||||||
'}';
|
'}';
|
||||||
}
|
}
|
||||||
|
|
|
@ -5,25 +5,47 @@ import java.nio.ByteBuffer;
|
||||||
import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.pod.definition.Encodable;
|
import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.pod.definition.Encodable;
|
||||||
|
|
||||||
public class LongInsulinProgramElement implements Encodable {
|
public class LongInsulinProgramElement implements Encodable {
|
||||||
|
private final byte startSlotIndex;
|
||||||
|
private final byte numberOfSlots;
|
||||||
private final short totalTenthPulses;
|
private final short totalTenthPulses;
|
||||||
private final int delayBetweenTenthPulses;
|
private final int delayBetweenTenthPulsesInUsec;
|
||||||
|
|
||||||
public LongInsulinProgramElement(byte totalTenthPulses, short delayBetweenTenthPulses) {
|
public LongInsulinProgramElement(byte startSlotIndex, byte numberOfSlots, short totalTenthPulses, int delayBetweenTenthPulsesInUsec) {
|
||||||
|
this.startSlotIndex = startSlotIndex;
|
||||||
|
this.numberOfSlots = numberOfSlots;
|
||||||
this.totalTenthPulses = totalTenthPulses;
|
this.totalTenthPulses = totalTenthPulses;
|
||||||
this.delayBetweenTenthPulses = delayBetweenTenthPulses;
|
this.delayBetweenTenthPulsesInUsec = delayBetweenTenthPulsesInUsec;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override public byte[] getEncoded() {
|
@Override public byte[] getEncoded() {
|
||||||
return ByteBuffer.allocate(6) //
|
return ByteBuffer.allocate(6) //
|
||||||
.putShort(totalTenthPulses) //
|
.putShort(totalTenthPulses) //
|
||||||
.putInt(delayBetweenTenthPulses) //
|
.putInt(delayBetweenTenthPulsesInUsec) //
|
||||||
.array();
|
.array();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public byte getStartSlotIndex() {
|
||||||
|
return startSlotIndex;
|
||||||
|
}
|
||||||
|
|
||||||
|
public byte getNumberOfSlots() {
|
||||||
|
return numberOfSlots;
|
||||||
|
}
|
||||||
|
|
||||||
|
public short getTotalTenthPulses() {
|
||||||
|
return totalTenthPulses;
|
||||||
|
}
|
||||||
|
|
||||||
|
public int getDelayBetweenTenthPulsesInUsec() {
|
||||||
|
return delayBetweenTenthPulsesInUsec;
|
||||||
|
}
|
||||||
|
|
||||||
@Override public String toString() {
|
@Override public String toString() {
|
||||||
return "LongInsulinProgramElement{" +
|
return "LongInsulinProgramElement{" +
|
||||||
"totalTenthPulses=" + totalTenthPulses +
|
"startSlotIndex=" + startSlotIndex +
|
||||||
", delayBetweenTenthPulses=" + delayBetweenTenthPulses +
|
", numberOfSlots=" + numberOfSlots +
|
||||||
|
", totalTenthPulses=" + totalTenthPulses +
|
||||||
|
", delayBetweenTenthPulsesInUsec=" + delayBetweenTenthPulsesInUsec +
|
||||||
'}';
|
'}';
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
package info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.pod.command.insulin.program;
|
package info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.pod.command.insulin.program;
|
||||||
|
|
||||||
|
import java.nio.ByteBuffer;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Calendar;
|
import java.util.Calendar;
|
||||||
import java.util.Date;
|
import java.util.Date;
|
||||||
|
@ -9,19 +10,39 @@ import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.pod.definitio
|
||||||
|
|
||||||
public final class ProgramBasalUtil {
|
public final class ProgramBasalUtil {
|
||||||
private static final byte NUMBER_OF_BASAL_SLOTS = 48;
|
private static final byte NUMBER_OF_BASAL_SLOTS = 48;
|
||||||
private static final byte MAX_NUMBER_OF_SLOTS_IN_SHORT_INSULIN_PROGRAM_ELEMENT = 16;
|
private static final byte MAX_NUMBER_OF_SLOTS_IN_INSULIN_PROGRAM_ELEMENT = 16;
|
||||||
|
private static final int NUMBER_OF_USEC_IN_SLOT = 1_800_000_000;
|
||||||
|
|
||||||
private ProgramBasalUtil() {
|
private ProgramBasalUtil() {
|
||||||
}
|
}
|
||||||
|
|
||||||
public static List<LongInsulinProgramElement> mapPulsesPerSlotToLongInsulinProgramElements(short[] pulsesPerSlot) {
|
public static List<LongInsulinProgramElement> mapPulsesPerSlotToLongInsulinProgramElements(short[] tenthPulsesPerSlot) {
|
||||||
if (pulsesPerSlot.length != NUMBER_OF_BASAL_SLOTS) {
|
if (tenthPulsesPerSlot.length != NUMBER_OF_BASAL_SLOTS) {
|
||||||
throw new IllegalArgumentException("Basal program must contain 48 slots");
|
throw new IllegalArgumentException("Basal program must contain 48 slots");
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO
|
List<LongInsulinProgramElement> elements = new ArrayList<>();
|
||||||
|
long previousTenthPulsesPerSlot = 0;
|
||||||
|
byte numberOfSlotsInCurrentElement = 0;
|
||||||
|
byte startSlotIndex = 0;
|
||||||
|
|
||||||
return new ArrayList<>();
|
for (int i = 0; i < NUMBER_OF_BASAL_SLOTS; i++) {
|
||||||
|
if (i == 0) {
|
||||||
|
previousTenthPulsesPerSlot = tenthPulsesPerSlot[i];
|
||||||
|
numberOfSlotsInCurrentElement = 1;
|
||||||
|
} else if (previousTenthPulsesPerSlot != tenthPulsesPerSlot[i] || numberOfSlotsInCurrentElement >= MAX_NUMBER_OF_SLOTS_IN_INSULIN_PROGRAM_ELEMENT) {
|
||||||
|
elements.add(new LongInsulinProgramElement(startSlotIndex, numberOfSlotsInCurrentElement, (short) (previousTenthPulsesPerSlot * numberOfSlotsInCurrentElement), (int) ((NUMBER_OF_USEC_IN_SLOT * numberOfSlotsInCurrentElement) / (previousTenthPulsesPerSlot * numberOfSlotsInCurrentElement))));
|
||||||
|
|
||||||
|
previousTenthPulsesPerSlot = tenthPulsesPerSlot[i];
|
||||||
|
numberOfSlotsInCurrentElement = 1;
|
||||||
|
startSlotIndex += numberOfSlotsInCurrentElement;
|
||||||
|
} else {
|
||||||
|
numberOfSlotsInCurrentElement++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
elements.add(new LongInsulinProgramElement(startSlotIndex, numberOfSlotsInCurrentElement, (short) (previousTenthPulsesPerSlot * numberOfSlotsInCurrentElement), (int) ((NUMBER_OF_USEC_IN_SLOT * numberOfSlotsInCurrentElement) / (previousTenthPulsesPerSlot * numberOfSlotsInCurrentElement))));
|
||||||
|
|
||||||
|
return elements;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static List<ShortInsulinProgramElement> mapPulsesPerSlotToShortInsulinProgramElements(short[] pulsesPerSlot) {
|
public static List<ShortInsulinProgramElement> mapPulsesPerSlotToShortInsulinProgramElements(short[] pulsesPerSlot) {
|
||||||
|
@ -45,7 +66,7 @@ public final class ProgramBasalUtil {
|
||||||
} else if (pulsesPerSlot[currentTotalNumberOfSlots] == previousPulsesPerSlot) {
|
} else if (pulsesPerSlot[currentTotalNumberOfSlots] == previousPulsesPerSlot) {
|
||||||
// Subsequent slot in element (same pulses per slot as previous slot)
|
// Subsequent slot in element (same pulses per slot as previous slot)
|
||||||
|
|
||||||
if (numberOfSlotsInCurrentElement < MAX_NUMBER_OF_SLOTS_IN_SHORT_INSULIN_PROGRAM_ELEMENT) {
|
if (numberOfSlotsInCurrentElement < MAX_NUMBER_OF_SLOTS_IN_INSULIN_PROGRAM_ELEMENT) {
|
||||||
numberOfSlotsInCurrentElement++;
|
numberOfSlotsInCurrentElement++;
|
||||||
} else {
|
} else {
|
||||||
elements.add(new ShortInsulinProgramElement(numberOfSlotsInCurrentElement, previousPulsesPerSlot, false));
|
elements.add(new ShortInsulinProgramElement(numberOfSlotsInCurrentElement, previousPulsesPerSlot, false));
|
||||||
|
@ -70,7 +91,7 @@ public final class ProgramBasalUtil {
|
||||||
currentTotalNumberOfSlots++;
|
currentTotalNumberOfSlots++;
|
||||||
expectAlternatePulseForNextSegment = !expectAlternatePulseForNextSegment;
|
expectAlternatePulseForNextSegment = !expectAlternatePulseForNextSegment;
|
||||||
|
|
||||||
if (numberOfSlotsInCurrentElement < MAX_NUMBER_OF_SLOTS_IN_SHORT_INSULIN_PROGRAM_ELEMENT) {
|
if (numberOfSlotsInCurrentElement < MAX_NUMBER_OF_SLOTS_IN_INSULIN_PROGRAM_ELEMENT) {
|
||||||
numberOfSlotsInCurrentElement++;
|
numberOfSlotsInCurrentElement++;
|
||||||
} else {
|
} else {
|
||||||
// End of alternate pulse segment (no slots left in element)
|
// End of alternate pulse segment (no slots left in element)
|
||||||
|
@ -110,6 +131,21 @@ public final class ProgramBasalUtil {
|
||||||
return elements;
|
return elements;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static short[] mapBasalProgramToTenthPulsesPerSlot(BasalProgram basalProgram) {
|
||||||
|
short[] tenthPulsesPerSlot = new short[NUMBER_OF_BASAL_SLOTS];
|
||||||
|
for (BasalProgram.Segment segment : basalProgram.getSegments()) {
|
||||||
|
for (int i = segment.getStartSlotIndex(); i < segment.getEndSlotIndex(); i++) {
|
||||||
|
tenthPulsesPerSlot[i] = (short) (roundToHalf(segment.getPulsesPerHour() / 2.0d) * 10);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return tenthPulsesPerSlot;
|
||||||
|
}
|
||||||
|
|
||||||
|
private static double roundToHalf(double d) {
|
||||||
|
return (double) (short) ((short) (int) (d * 10.0d) / 5 * 5) / 10.0d;
|
||||||
|
}
|
||||||
|
|
||||||
public static short[] mapBasalProgramToPulsesPerSlot(BasalProgram basalProgram) {
|
public static short[] mapBasalProgramToPulsesPerSlot(BasalProgram basalProgram) {
|
||||||
short[] pulsesPerSlot = new short[NUMBER_OF_BASAL_SLOTS];
|
short[] pulsesPerSlot = new short[NUMBER_OF_BASAL_SLOTS];
|
||||||
for (BasalProgram.Segment segment : basalProgram.getSegments()) {
|
for (BasalProgram.Segment segment : basalProgram.getSegments()) {
|
||||||
|
@ -137,14 +173,75 @@ public final class ProgramBasalUtil {
|
||||||
int secondOfMinute = instance.get(Calendar.SECOND);
|
int secondOfMinute = instance.get(Calendar.SECOND);
|
||||||
|
|
||||||
byte index = (byte) ((hourOfDay * 60 + minuteOfHour) / 30);
|
byte index = (byte) ((hourOfDay * 60 + minuteOfHour) / 30);
|
||||||
short secondsRemaining = (short) ((index + 1) * 1800 - (secondOfMinute + hourOfDay * 3600 + minuteOfHour * 60));
|
int secondOfDay = secondOfMinute + hourOfDay * 3_600 + minuteOfHour * 60;
|
||||||
short pulsesRemaining = (short) ((double) pulsesPerSlot[index] * secondsRemaining / 1800);
|
|
||||||
|
|
||||||
return new CurrentSlot(index, secondsRemaining, pulsesRemaining);
|
short secondsRemaining = (short) ((index + 1) * 1_800 - secondOfDay);
|
||||||
|
short pulsesRemaining = (short) ((double) pulsesPerSlot[index] * secondsRemaining / 1_800);
|
||||||
|
|
||||||
|
return new CurrentSlot(index, (short) (secondsRemaining * 8), pulsesRemaining);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static short createChecksum() {
|
public static CurrentLongInsulinProgramElement calculateCurrentLongInsulinProgramElement(List<LongInsulinProgramElement> elements, Date currentTime) {
|
||||||
// TODO
|
Calendar instance = Calendar.getInstance();
|
||||||
return 0;
|
instance.setTime(currentTime);
|
||||||
|
|
||||||
|
int hourOfDay = instance.get(Calendar.HOUR_OF_DAY);
|
||||||
|
int minuteOfHour = instance.get(Calendar.MINUTE);
|
||||||
|
int secondOfMinute = instance.get(Calendar.SECOND);
|
||||||
|
|
||||||
|
int secondOfDay = secondOfMinute + hourOfDay * 3_600 + minuteOfHour * 60;
|
||||||
|
int startSlotIndex = 0;
|
||||||
|
|
||||||
|
byte index = 0;
|
||||||
|
for (LongInsulinProgramElement element : elements) {
|
||||||
|
int startTimeInSeconds = startSlotIndex * 1_800;
|
||||||
|
int endTimeInSeconds = startTimeInSeconds + element.getNumberOfSlots() * 1_800;
|
||||||
|
|
||||||
|
if (secondOfDay >= startTimeInSeconds && secondOfDay < endTimeInSeconds) {
|
||||||
|
long totalNumberOfTenThousandthPulsesInSlot = element.getTotalTenthPulses() * 1_000;
|
||||||
|
if (totalNumberOfTenThousandthPulsesInSlot == 0) {
|
||||||
|
totalNumberOfTenThousandthPulsesInSlot = element.getNumberOfSlots() * 1_000;
|
||||||
|
}
|
||||||
|
|
||||||
|
int durationInSeconds = endTimeInSeconds - startTimeInSeconds;
|
||||||
|
int secondsPassedInCurrentSlot = secondOfDay - startTimeInSeconds;
|
||||||
|
long remainingTenThousandthPulses = (durationInSeconds - secondsPassedInCurrentSlot) * (long) totalNumberOfTenThousandthPulsesInSlot;
|
||||||
|
int delayBetweenTenthPulsesInUsec = (int) (durationInSeconds * 1_000_000L * 1_000 / totalNumberOfTenThousandthPulsesInSlot);
|
||||||
|
int secondsRemaining = secondsPassedInCurrentSlot % 1_800;
|
||||||
|
int delayUntilNextTenthPulseInUsec = delayBetweenTenthPulsesInUsec;
|
||||||
|
for (int i = 0; i < secondsRemaining; i++) {
|
||||||
|
delayUntilNextTenthPulseInUsec = delayUntilNextTenthPulseInUsec - 1_000_000;
|
||||||
|
while (delayUntilNextTenthPulseInUsec <= 0) {
|
||||||
|
delayUntilNextTenthPulseInUsec += delayBetweenTenthPulsesInUsec;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
short remainingTenthPulses = (short) ((0 != remainingTenThousandthPulses % 1_000 ? 1 : 0) + remainingTenThousandthPulses / 1_000);
|
||||||
|
|
||||||
|
return new CurrentLongInsulinProgramElement(index, delayUntilNextTenthPulseInUsec, remainingTenthPulses);
|
||||||
|
}
|
||||||
|
|
||||||
|
index++;
|
||||||
|
startSlotIndex += element.getNumberOfSlots();
|
||||||
|
}
|
||||||
|
throw new IllegalStateException("Could not determine current long insulin program element");
|
||||||
|
}
|
||||||
|
|
||||||
|
public static short createChecksum(short[] pulsesPerSlot, CurrentSlot currentSlot) {
|
||||||
|
ByteBuffer buffer = ByteBuffer.allocate(1 + 2 + 2 + NUMBER_OF_BASAL_SLOTS * 2) //
|
||||||
|
.put(currentSlot.getIndex()) //
|
||||||
|
.putShort(currentSlot.getPulsesRemaining()) //
|
||||||
|
.putShort(currentSlot.getEighthSecondsRemaining());
|
||||||
|
|
||||||
|
for (short pulses : pulsesPerSlot) {
|
||||||
|
buffer.putShort(pulses);
|
||||||
|
}
|
||||||
|
|
||||||
|
byte[] bytes = buffer.array();
|
||||||
|
|
||||||
|
short sum = 0;
|
||||||
|
for (byte b : bytes) {
|
||||||
|
sum += (short) (b & 0xff);
|
||||||
|
}
|
||||||
|
return sum;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue