Set up the hubs to auto-calibrate voltage to a target automatically on first startup to alleviate the need for manual calibration.

This commit is contained in:
Mark Milligan 2021-01-20 21:55:29 -06:00
parent 3d7f116baa
commit 6c6f750691
4 changed files with 66 additions and 4 deletions

View File

@ -62,6 +62,39 @@ public class CurrentMonitor {
debug = _debug;
}
public double calibrateVoltage(double _curCalibration, float _voltage) {
GpioPinAnalogInput voltagePin = getPin(0, 0);
if (voltagePin == null)
return 0.0;
List<Double> samples = new ArrayList<>(120000);
long intervalEnd = System.nanoTime() + 2000000000L; //Scan voltage for 2 seconds
while (System.nanoTime() < intervalEnd) {
samples.add(voltagePin.getValue());
}
double vOffset = 0.0;
for (Double sample : samples) {
vOffset += sample;
}
vOffset /= samples.size();
double vRms = 0.0;
for (Double sample : samples) {
sample -= vOffset;
vRms += sample * sample;
}
vRms /= samples.size();
double oldVrms = _curCalibration * Math.sqrt(vRms);
if (oldVrms < 20) {
LOG.info("Could not get a valid voltage read, please check that your AC/AC transformer is connected");
return 0.0;
}
double newCal = (_voltage/oldVrms) * _curCalibration;
double newVrms = newCal * Math.sqrt(vRms);
LOG.info("Old Voltage Calibration: {} Old vRMS: {}", _curCalibration, oldVrms);
LOG.info("New Voltage Calibration: {} New vRMS: {}", newCal, newVrms);
return newCal;
}
public void monitorPower(BreakerHub _hub, List<Breaker> _breakers, int _intervalMs, PowerListener _listener) {
stopMonitoring();
listener = _listener;

View File

@ -179,9 +179,17 @@ public class MonitorApp {
ConcurrencyUtils.sleep(5000);
}
LOG.info("Breaker Config loaded");
LOG.debug(DaoSerializer.toJson(breakerConfig));
BreakerHub hub = breakerConfig.getHub(config.getHub());
if (hub != null) {
if (config.isNeedsCalibration() && (config.getAutoCalibrationVoltage() != 0.0)) {
double newCal = monitor.calibrateVoltage(hub.getVoltageCalibrationFactor(), config.getAutoCalibrationVoltage());
if (newCal != 0.0) {
hub.setVoltageCalibrationFactor(newCal);
config.setNeedsCalibration(false);
ResourceLoader.writeFile(WORKING_DIR + "config.json", DaoSerializer.toJson(config));
post(DaoSerializer.toZipBson(breakerConfig), "currentmonitor/config");
}
}
List<Breaker> breakers = breakerConfig.getBreakersForHub(config.getHub());
LOG.info("Monitoring {} breakers for hub {}", CollectionUtils.size(breakers), hub.getHub());
monitor.monitorPower(hub, breakers, 1000, logger);

View File

@ -14,6 +14,8 @@ public class MonitorConfig {
private int connectTimeout;
private int socketTimeout;
private int updateInterval;
private float autoCalibrationVoltage;
private boolean needsCalibration;
public MonitorConfig() {
}
@ -94,4 +96,20 @@ public class MonitorConfig {
public void setUpdateInterval(int _updateInterval) {
updateInterval = _updateInterval;
}
public float getAutoCalibrationVoltage() {
return autoCalibrationVoltage;
}
public void setAutoCalibrationVoltage(float _autoCalibrationVoltage) {
autoCalibrationVoltage = _autoCalibrationVoltage;
}
public boolean isNeedsCalibration() {
return needsCalibration;
}
public void setNeedsCalibration(boolean _needsCalibration) {
needsCalibration = _needsCalibration;
}
}

View File

@ -5,7 +5,6 @@ import com.lanternsoftware.util.dao.AbstractDaoSerializer;
import com.lanternsoftware.util.dao.DaoEntity;
import com.lanternsoftware.util.dao.DaoProxyType;
import com.lanternsoftware.util.dao.DaoSerializer;
import java.util.Collections;
import java.util.List;
@ -32,9 +31,11 @@ public class MonitorConfigSerializer extends AbstractDaoSerializer<MonitorConfig
d.put("password", _o.getPassword());
d.put("hub", _o.getHub());
d.put("debug", _o.isDebug());
d.put("socket_timeout", _o.getSocketTimeout());
d.put("connect_timeout", _o.getConnectTimeout());
d.put("socket_timeout", _o.getSocketTimeout());
d.put("update_interval", _o.getUpdateInterval());
d.put("auto_calibration_voltage", _o.getAutoCalibrationVoltage());
d.put("needs_calibration", _o.isNeedsCalibration());
return d;
}
@ -48,9 +49,11 @@ public class MonitorConfigSerializer extends AbstractDaoSerializer<MonitorConfig
o.setPassword(DaoSerializer.getString(_d, "password"));
o.setHub(DaoSerializer.getInteger(_d, "hub"));
o.setDebug(DaoSerializer.getBoolean(_d, "debug"));
o.setSocketTimeout(DaoSerializer.getInteger(_d, "socket_timeout"));
o.setConnectTimeout(DaoSerializer.getInteger(_d, "connect_timeout"));
o.setSocketTimeout(DaoSerializer.getInteger(_d, "socket_timeout"));
o.setUpdateInterval(DaoSerializer.getInteger(_d, "update_interval"));
o.setAutoCalibrationVoltage(DaoSerializer.getFloat(_d, "auto_calibration_voltage"));
o.setNeedsCalibration(DaoSerializer.getBoolean(_d, "needs_calibration"));
return o;
}
}