Skip to content

Commit

Permalink
Merge pull request #88 from voroshkov/api-v4
Browse files Browse the repository at this point in the history
Api v4
  • Loading branch information
voroshkov authored May 28, 2018
2 parents 7d383f3 + 5b0f7c1 commit 4dc0670
Show file tree
Hide file tree
Showing 26 changed files with 806 additions and 408 deletions.
6 changes: 3 additions & 3 deletions Android/ChorusRFLaptimer/app/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -2,13 +2,13 @@ apply plugin: 'com.android.application'

android {
compileSdkVersion 25
buildToolsVersion '25.0.2'
buildToolsVersion '26.0.2'
defaultConfig {
applicationId "app.andrey_voroshkov.chorus_laptimer"
minSdkVersion 16
targetSdkVersion 25
versionCode 17
versionName "0.7.5"
versionCode 18
versionName "0.7.6"
testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"
archivesBaseName = "ChorusRFLaptimer"
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -207,19 +207,19 @@ public static void applyDeviceDependentPreferences() {
boolean prefSkipFirstLap = app.preferences.getBoolean(SKIP_FIRST_LAP, true);
if (app.shouldSkipFirstLap != prefSkipFirstLap) {
app.changeSkipFirstLap(prefSkipFirstLap);
app.sendBtCommand("R*F");
app.sendBtCommand("R*1" + (prefSkipFirstLap ? "0" : "1"));
}

boolean prefEnableDeviceSounds = app.preferences.getBoolean(ENABLE_DEVICE_SOUNDS, true);
if (app.isDeviceSoundEnabled != prefEnableDeviceSounds) {
app.changeDeviceSoundState(prefEnableDeviceSounds);
app.sendBtCommand("R*D");
app.sendBtCommand("R*S" + (prefEnableDeviceSounds ? "1" : "0"));
}

if (app.raceState != null) {
int prefMLT = app.preferences.getInt(MIN_LAP_TIME, 3);
app.changeRaceMinLapTime(prefMLT);
app.sendBtCommand("R*L" + String.format("%02X", prefMLT));
app.sendBtCommand("R*M" + String.format("%02X", prefMLT));
}

if (app.deviceStates != null) {
Expand All @@ -233,7 +233,7 @@ public static void applyDeviceDependentPreferences() {
if (i < bandsCount) {
int prefBand = Integer.parseInt(bandsArray[i]);
app.changeDeviceBand(i, prefBand);
app.sendBtCommand("R" + String.format("%X", i) + "N" + String.format("%X", prefBand));
app.sendBtCommand("R" + String.format("%X", i) + "B" + String.format("%X", prefBand));
}
}
}
Expand All @@ -248,7 +248,7 @@ public static void applyDeviceDependentPreferences() {
if (i < channelsCount) {
int prefChannel = Integer.parseInt(channelsArray[i]);
app.changeDeviceChannel(i, prefChannel);
app.sendBtCommand("R" + String.format("%X", i) + "H" + String.format("%X", prefChannel));
app.sendBtCommand("R" + String.format("%X", i) + "C" + String.format("%X", prefChannel));
}
}
}
Expand All @@ -263,7 +263,7 @@ public static void applyDeviceDependentPreferences() {
if (i < thresholdsCount) {
int prefThreshold = Integer.parseInt(thresholdsArray[i]);
app.changeDeviceThreshold(i, prefThreshold);
app.sendBtCommand("R" + String.format("%X", i) + "S" + String.format("%04X", prefThreshold));
app.sendBtCommand("R" + String.format("%X", i) + "T" + String.format("%04X", prefThreshold));
}
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
import android.os.Handler;
import android.os.Message;
import android.support.annotation.StringRes;
import android.text.TextUtils;

import java.util.ArrayList;

Expand All @@ -17,13 +18,17 @@
public class AppState {
public static final byte DELIMITER = '\n';

public static final int SUPPORTED_API_VERSION = 4;

public static final int MIN_RSSI = 80;
public static final int MAX_RSSI = 315;
public static final int RSSI_SPAN = MAX_RSSI - MIN_RSSI;
public static final int CALIBRATION_TIME_MS = 10000;
public static final String bandNames [] = {"R", "A", "B", "E", "F", "D", "Connex1", "Connex2"};
public static final int DEFAULT_MIN_LAP_TIME = 5;
public static final int DEFAULT_LAPS_TO_GO = 3;
public static final int NO_API_VERSION = -1;
public static final int NO_TIME_ADJUSTMENT = 0x7FFFFFF;

//tone sounds and durations (race start, lap count, etc)
public static final int TONE_PREPARE = ToneGenerator.TONE_DTMF_1;
Expand All @@ -33,6 +38,7 @@ public class AppState {
public static final int TONE_LAP = ToneGenerator.TONE_DTMF_S;
public static final int DURATION_LAP = 400;
public static final int MIN_TIME_BEFORE_RACE_TO_SPEAK = 5; //seconds, don't speak "Prepare" message if less time is set
public static final int START_BEEPS_COUNT = 4; //number of beeps in start beeps sequence. should be within 1 - 16

//voltage measuring constants
public static final int BATTERY_CHECK_INTERVAL = 10000; // 10 seconds
Expand Down Expand Up @@ -76,6 +82,8 @@ public static AppState getInstance() {
public int batteryAdjustmentConst = 1;
public boolean isLiPoMonitorEnabled = true;
public boolean isConnected = false;
public int calibrationActualTime = 10000;
public boolean didWrongApiEventFire = false;

private ArrayList<Boolean> deviceTransmissionStates;
private ArrayList<IDataListener> mListeners;
Expand All @@ -94,7 +102,7 @@ private AppState() {
public void handleMessage(Message msg) {
AppState app = AppState.getInstance();
if (app.isConnected && app.isLiPoMonitorEnabled && app.raceState != null && !app.raceState.isStarted) {
AppState.getInstance().sendBtCommand("R*Y");
AppState.getInstance().sendBtCommand("R*v");
}
sendEmptyMessageDelayed(0, BATTERY_CHECK_INTERVAL);
}
Expand Down Expand Up @@ -324,6 +332,13 @@ public String getBandText(int deviceId) {
}
}

public int getThresholdSetupState(int deviceId) {
if (deviceStates == null) return 0;
if (deviceStates.size() <= deviceId) return 0;
int thresholdSetupState = deviceStates.get(deviceId).thresholdSetupState;
return thresholdSetupState;
}

// Channels to send to the SPI registers
private static int channelTable[] = {
// Channel 1 - 8
Expand Down Expand Up @@ -408,6 +423,7 @@ public int getEnabledPilotsCount() {
//---------------------------------------------------------------------
public void sendBtCommand(String cmd) {
if (conn == null) return;
// Log.i("SEND BT COMMAND", cmd);
conn.send(cmd + (char)DELIMITER);
}

Expand All @@ -426,7 +442,7 @@ public void onDisconnected() {
}

public void onBeforeDisconnect() {
sendBtCommand("R*v"); // turn off RSSI monitoring before disconnect
sendBtCommand("R*I0000"); // turn off RSSI monitoring before disconnect
suspendBatteryMonitoringHandlers();
}
//---------------------------------------------------------------------
Expand Down Expand Up @@ -455,14 +471,54 @@ public void setNumberOfDevices(int n) {
emitEvent(DataAction.NDevices);

resetDeviceTransmissionStates();
sendBtCommand("R*A");
clearApiVersions();
clearWrongApiWarningCounter();
sendBtCommand("R*#");
sendBtCommand("R*a");
}

public void resetDeviceTransmissionStates() {
for(int i=0; i<deviceTransmissionStates.size(); i++) {
deviceTransmissionStates.set(i, false);
}
}
public void checkApiVersion(int deviceId, int version) {
DeviceState currentState = deviceStates.get(deviceId);
if (currentState == null) {
return;
}
currentState.apiVersion = version;

boolean doHaveAllVersions = true;
for (DeviceState ds: deviceStates) {
int ver = ds.apiVersion;
if (ver == NO_API_VERSION) {
doHaveAllVersions = false;
break;
}
}
if (doHaveAllVersions) {
if (!getModulesWithWrongApiVersion().equals("") && !didWrongApiEventFire) {
emitEvent(DataAction.WrongApiVersion);
didWrongApiEventFire = true;
}
}
}

public String getModulesWithWrongApiVersion() {
boolean isAnyWrong = false;
ArrayList<String> wrongsList = new ArrayList<>();
int count = deviceStates.size();
for(int i = 0; i < count; i++) {
DeviceState ds = deviceStates.get(i);
if (ds.apiVersion < SUPPORTED_API_VERSION) {
isAnyWrong = true;
wrongsList.add(Integer.toString(i + 1));
}
}
if (!isAnyWrong) return "";
return TextUtils.join(", ", wrongsList);
}

public void changeDeviceChannel(int deviceId, int channel) {
DeviceState currentState = deviceStates.get(deviceId);
Expand Down Expand Up @@ -670,6 +726,18 @@ public void addLapResult(int deviceId, int lapNumber, int lapTime) {
}
}
}
public void clearOldCalibrationTimes() {
calibrationActualTime = 0;
for (DeviceState ds: deviceStates) {
ds.isCalibrated = false;
ds.calibrationTime = 0;
ds.deviceTime = 0;
}
}

public void setCalibrationActualTime(int calibrationActualTime) {
this.calibrationActualTime = calibrationActualTime;
}

public void changeCalibration(int deviceId, boolean isCalibrated) {
if (deviceId >= numberOfDevices) {
Expand All @@ -683,15 +751,23 @@ public void changeCalibration(int deviceId, boolean isCalibrated) {
emitEvent(DataAction.DeviceCalibrationStatus);
}

public void changeDeviceCalibrationTime(int deviceId, int calibrationTime) {
public void changeDeviceCalibrationTime(int deviceId, long deviceTime) {
if (deviceId >= numberOfDevices) {
return;
}
DeviceState currentState = deviceStates.get(deviceId);
if (currentState == null) {
return;
}

if (currentState.deviceTime == 0) {
currentState.deviceTime = deviceTime; // first read? just store current time into device state
return;
}

int calibrationTime = (int)(deviceTime - currentState.deviceTime); // find diff between this time and previous read
currentState.calibrationTime = calibrationTime;
currentState.deviceTime = 0; // just drop prev read to avoid possible mistakes in future
boolean doHaveAllTimes = true;
for (DeviceState ds: deviceStates) {
int time = ds.calibrationTime;
Expand All @@ -706,16 +782,18 @@ public void changeDeviceCalibrationTime(int deviceId, int calibrationTime) {
}

public void calculateAndSendCalibrationValues() {
int baseTime = CALIBRATION_TIME_MS;
int baseTime = calibrationActualTime;
for (int i = 0; i < numberOfDevices; i++) {
int time = deviceStates.get(i).calibrationTime;

int diff = baseTime - time;
int calibrationValue = 0;

int calibrationValue = NO_TIME_ADJUSTMENT; // predefined const
if (diff != 0) {
calibrationValue = baseTime/diff;
}
deviceStates.get(i).calibrationValue = calibrationValue;
sendBtCommand("C" + String.format("%X", i) + String.format("%08X", calibrationValue));
sendBtCommand("R" + String.format("%X", i) + "J" + String.format("%08X", calibrationValue));
}
emitEvent(DataAction.DeviceCalibrationValue);
}
Expand All @@ -732,6 +810,18 @@ public void changeRssiMonitorState(boolean isMonitorOn) {
emitEvent(DataAction.RSSImonitorState);
}

public void changeThresholdSetupState(int deviceId, int thrSetupState) {
if (deviceId >= numberOfDevices) {
return;
}
DeviceState currentState = deviceStates.get(deviceId);
if (currentState == null) {
return;
}
currentState.thresholdSetupState = thrSetupState;
emitEvent(DataAction.ThresholdSetupState);
}

//use to determine if all devices reported their state after connection
public boolean isDevicesInitializationOver() {
int count = deviceTransmissionStates.size();
Expand All @@ -755,10 +845,10 @@ public void receivedEndOfSequence(int deviceId) {
return;
}
if (raceState.isStarted && isRssiMonitorOn) {
sendBtCommand("R*v"); // turn RSSI Monitoring off
sendBtCommand("R*I0000"); // turn RSSI Monitoring off
}
if (!raceState.isStarted && !isRssiMonitorOn) {
sendBtCommand("R*V"); // turn RSSI Monitoring on
sendBtCommand("R*I0064"); // turn RSSI Monitoring on
}
//also decide to apply preferences after all states are received
AppPreferences.applyInAppPreferences();
Expand Down Expand Up @@ -829,6 +919,17 @@ public void clearVoltage() {
recalculateVoltage();
}

public void clearWrongApiWarningCounter() {
didWrongApiEventFire = false;
}

public void clearApiVersions() {
int count = deviceStates.size();
for(int i = 0; i < count; i++) {
deviceStates.get(i).apiVersion = NO_API_VERSION;
}
}

public void changeAdjustmentConst(int adjConst) {
if (!isLiPoMonitorEnabled) {
return;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -93,28 +93,40 @@ public View getView(final int position, View convertView, ViewGroup parent) {
viewHolder.btnDecCh.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
AppState.getInstance().sendBtCommand("R" + deviceId + "c");
int newChannel = AppState.getInstance().deviceStates.get(position).channel - 1;
if (newChannel >= 0) {
AppState.getInstance().sendBtCommand("R" + deviceId + "C" + String.format("%X", newChannel));
}
}
});

viewHolder.btnIncCh.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
AppState.getInstance().sendBtCommand("R" + deviceId + "C");
int newChannel = AppState.getInstance().deviceStates.get(position).channel + 1;
if (newChannel <= 7) {
AppState.getInstance().sendBtCommand("R" + deviceId + "C" + String.format("%X", newChannel));
}
}
});

viewHolder.btnDecBand.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
AppState.getInstance().sendBtCommand("R" + deviceId + "b");
int newBand = AppState.getInstance().deviceStates.get(position).band - 1;
if (newBand >= 0) {
AppState.getInstance().sendBtCommand("R" + deviceId + "B" + String.format("%X", newBand));
}
}
});

viewHolder.btnIncBand.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
AppState.getInstance().sendBtCommand("R" + deviceId + "B");
int newBand = AppState.getInstance().deviceStates.get(position).band + 1;
if (newBand <= 6) {
AppState.getInstance().sendBtCommand("R" + deviceId + "B" + String.format("%X", newBand));
}
}
});

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -30,5 +30,7 @@ public enum DataAction {
BatteryVoltage,
VoltageAdjustmentConst,
LiPoMonitorEnable,
WrongApiVersion,
ThresholdSetupState,
Disconnect
}
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,9 @@ public class DeviceState {
public int calibrationValue;
public int currentRSSI;
public boolean isEnabled;
public long deviceTime;
public int thresholdSetupState;
public int apiVersion;

DeviceState() {
isCalibrated = false;
Expand Down
Loading

0 comments on commit 4dc0670

Please sign in to comment.