mirror of
https://github.com/letscontrolit/ESPEasy.git
synced 2026-07-27 19:57:38 +00:00
[Cleanup] Reduce build size by using float instead of double in rules
This commit is contained in:
@@ -29,20 +29,6 @@
|
||||
/* PRIVATE FUNCTIONS */
|
||||
/*========================================================================*/
|
||||
|
||||
/**************************************************************************/
|
||||
/*!
|
||||
* @brief Implements missing powf function
|
||||
* @param x
|
||||
* Base number
|
||||
* @param y
|
||||
* Exponent
|
||||
* @return x raised to the power of y
|
||||
*/
|
||||
/**************************************************************************/
|
||||
float powf(const float x, const float y)
|
||||
{
|
||||
return (float)(pow((double)x, (double)y));
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
/*!
|
||||
|
||||
+1
-1
@@ -493,7 +493,7 @@ boolean Plugin_016(uint8_t function, struct EventStruct *event, String& string)
|
||||
# if P016_FEATURE_COMMAND_HANDLING
|
||||
P016_CMDINHIBIT = getFormItemInt(F("pcmdinhibit"));
|
||||
# endif // if P016_FEATURE_COMMAND_HANDLING
|
||||
P016_BUFFERSIZE = ceil(getFormItemInt(F("pbuffersize")) / 2.0f); // UI shows bytes, we store buffer unit = uint16_t
|
||||
P016_BUFFERSIZE = (getFormItemInt(F("pbuffersize")) + 1) >> 1; // UI shows bytes, we store buffer unit = uint16_t
|
||||
|
||||
# if P016_FEATURE_COMMAND_HANDLING
|
||||
|
||||
|
||||
+2
-2
@@ -131,10 +131,10 @@ boolean Plugin_021(uint8_t function, struct EventStruct *event, String& string)
|
||||
|
||||
if (equals(command, F("setlevel"))) {
|
||||
String value = parseString(string, 2);
|
||||
double result = 0.0;
|
||||
ESPEASY_RULES_FLOAT_TYPE result{};
|
||||
|
||||
if (!isError(Calculate(value, result))) {
|
||||
if (!essentiallyEqual(static_cast<double>(P021_TRIGGER_LEVEL), result)) { // Save only if different
|
||||
if (!essentiallyEqual(static_cast<ESPEASY_RULES_FLOAT_TYPE>(P021_TRIGGER_LEVEL), result)) { // Save only if different
|
||||
P021_TRIGGER_LEVEL = result;
|
||||
|
||||
if (P021_DONT_ALWAYS_SAVE == 0) { // save only if explicitly enabled
|
||||
|
||||
@@ -1200,7 +1200,7 @@ boolean Plugin_036(uint8_t function, struct EventStruct *event, String& string)
|
||||
|
||||
if (strlen > 0) {
|
||||
const float fAvgPixPerChar = static_cast<float>(PixLength) / strlen;
|
||||
const int iCharToRemove = ceil((static_cast<float>(PixLength - 255)) / fAvgPixPerChar);
|
||||
const int iCharToRemove = ceilf((static_cast<float>(PixLength - 255)) / fAvgPixPerChar);
|
||||
|
||||
// shorten string because OLED controller can not handle such long strings
|
||||
*currentLine = currentLine->substring(0, strlen - iCharToRemove);
|
||||
|
||||
@@ -589,7 +589,7 @@ boolean Plugin_037(uint8_t function, struct EventStruct *event, String& string)
|
||||
bool numericPayload = true; // Unless it's not
|
||||
|
||||
if (!checkJson || (checkJson && (!key.isEmpty()))) {
|
||||
double doublePayload;
|
||||
ESPEASY_RULES_FLOAT_TYPE doublePayload{};
|
||||
|
||||
if (!validDoubleFromString(Payload, doublePayload)) {
|
||||
if (!checkJson && (P037_SEND_EVENTS == 0)) { // If we want all values as events, then no error logged and don't stop here
|
||||
|
||||
@@ -128,7 +128,7 @@ boolean Plugin_071(uint8_t function, struct EventStruct *event, String& string)
|
||||
i = 0;
|
||||
parityerrors = 0;
|
||||
char *tmpstr;
|
||||
double m_energy, m_volume;
|
||||
ESPEASY_RULES_FLOAT_TYPE m_energy, m_volume;
|
||||
float m_tempin, m_tempout, m_tempdiff, m_power;
|
||||
long m_hours, m_flow;
|
||||
|
||||
|
||||
+34
-9
@@ -228,16 +228,31 @@ boolean Plugin_076(uint8_t function, struct EventStruct *event, String& string)
|
||||
}
|
||||
|
||||
|
||||
double current, voltage, power;
|
||||
ESPEASY_RULES_FLOAT_TYPE current, voltage, power;
|
||||
|
||||
if (Plugin076_LoadMultipliers(event->TaskIndex, current, voltage, power)) {
|
||||
addFormSubHeader(F("Calibration Values"));
|
||||
addFormTextBox(F("Current Multiplier"), F("currmult"),
|
||||
doubleToString(current, 2), 25);
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
doubleToString(current, 2)
|
||||
#else
|
||||
floatToString(current, 2)
|
||||
#endif
|
||||
, 25);
|
||||
addFormTextBox(F("Voltage Multiplier"), F("voltmult"),
|
||||
doubleToString(voltage, 2), 25);
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
doubleToString(voltage, 2)
|
||||
#else
|
||||
floatToString(voltage, 2)
|
||||
#endif
|
||||
, 25);
|
||||
addFormTextBox(F("Power Multiplier"), F("powmult"),
|
||||
doubleToString(power, 2), 25);
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
doubleToString(power, 2)
|
||||
#else
|
||||
floatToString(power, 2)
|
||||
#endif
|
||||
, 25);
|
||||
}
|
||||
|
||||
success = true;
|
||||
@@ -268,7 +283,7 @@ boolean Plugin_076(uint8_t function, struct EventStruct *event, String& string)
|
||||
}
|
||||
|
||||
// Set Multipliers
|
||||
double hlwMultipliers[3];
|
||||
ESPEASY_RULES_FLOAT_TYPE hlwMultipliers[3];
|
||||
hlwMultipliers[0] = getFormItemFloat(F("currmult"));
|
||||
hlwMultipliers[1] = getFormItemFloat(F("voltmult"));
|
||||
hlwMultipliers[2] = getFormItemFloat(F("powmult"));
|
||||
@@ -438,7 +453,7 @@ boolean Plugin_076(uint8_t function, struct EventStruct *event, String& string)
|
||||
}
|
||||
# endif // ifndef BUILD_NO_DEBUG
|
||||
|
||||
double current, voltage, power;
|
||||
ESPEASY_RULES_FLOAT_TYPE current, voltage, power;
|
||||
|
||||
if (Plugin076_LoadMultipliers(event->TaskIndex, current, voltage, power)) {
|
||||
# ifndef BUILD_NO_DEBUG
|
||||
@@ -554,15 +569,25 @@ void Plugin076_SaveMultipliers() {
|
||||
if (StoredTaskIndex < 0) {
|
||||
return; // Not yet initialized.
|
||||
}
|
||||
double hlwMultipliers[3]{};
|
||||
ESPEASY_RULES_FLOAT_TYPE hlwMultipliers[3]{};
|
||||
|
||||
if (Plugin076_ReadMultipliers(hlwMultipliers[0], hlwMultipliers[1], hlwMultipliers[2])) {
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
SaveCustomTaskSettings(StoredTaskIndex, reinterpret_cast<const uint8_t *>(&hlwMultipliers),
|
||||
sizeof(hlwMultipliers));
|
||||
#else
|
||||
double hlwMultipliers_d[3]{};
|
||||
hlwMultipliers_d[0] = hlwMultipliers[0];
|
||||
hlwMultipliers_d[1] = hlwMultipliers[1];
|
||||
hlwMultipliers_d[2] = hlwMultipliers[2];
|
||||
|
||||
SaveCustomTaskSettings(StoredTaskIndex, reinterpret_cast<const uint8_t *>(&hlwMultipliers_d),
|
||||
sizeof(hlwMultipliers_d));
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
bool Plugin076_ReadMultipliers(double& current, double& voltage, double& power) {
|
||||
bool Plugin076_ReadMultipliers(ESPEASY_RULES_FLOAT_TYPE& current, ESPEASY_RULES_FLOAT_TYPE& voltage, ESPEASY_RULES_FLOAT_TYPE& power) {
|
||||
current = 0.0f;
|
||||
voltage = 0.0f;
|
||||
power = 0.0f;
|
||||
@@ -576,7 +601,7 @@ bool Plugin076_ReadMultipliers(double& current, double& voltage, double& power)
|
||||
return false;
|
||||
}
|
||||
|
||||
bool Plugin076_LoadMultipliers(taskIndex_t TaskIndex, double& current, double& voltage, double& power) {
|
||||
bool Plugin076_LoadMultipliers(taskIndex_t TaskIndex, ESPEASY_RULES_FLOAT_TYPE& current, ESPEASY_RULES_FLOAT_TYPE& voltage, ESPEASY_RULES_FLOAT_TYPE& power) {
|
||||
// If multipliers are empty load default ones and save all of them as
|
||||
// "CustomTaskSettings"
|
||||
if (!Plugin076_ReadMultipliers(current, voltage, power)) {
|
||||
|
||||
+5
-5
@@ -426,7 +426,7 @@ boolean Plugin_082(uint8_t function, struct EventStruct *event, String& string)
|
||||
}
|
||||
activeFix = curFixStatus;
|
||||
}
|
||||
double distance = 0.0;
|
||||
ESPEASY_RULES_FLOAT_TYPE distance{};
|
||||
|
||||
if (curFixStatus) {
|
||||
if (P082_data->gps->location.isUpdated()) {
|
||||
@@ -482,12 +482,12 @@ boolean Plugin_082(uint8_t function, struct EventStruct *event, String& string)
|
||||
|
||||
if (P082_DISTANCE > 0) {
|
||||
// Check travelled distance.
|
||||
if ((distance > static_cast<double>(P082_DISTANCE)) || (distance < 0.0)) {
|
||||
if ((distance > static_cast<ESPEASY_RULES_FLOAT_TYPE>(P082_DISTANCE)) || (distance < 0)) {
|
||||
if (P082_data->storeCurPos(P082_TIMEOUT)) {
|
||||
distance_passed = true;
|
||||
|
||||
// Add sanity check for distance travelled
|
||||
if (distance > static_cast<double>(P082_DISTANCE)) {
|
||||
if (distance > static_cast<ESPEASY_RULES_FLOAT_TYPE>(P082_DISTANCE)) {
|
||||
if (Settings.UseRules) {
|
||||
String eventString = F("GPS#travelled=");
|
||||
eventString += distance;
|
||||
@@ -813,8 +813,8 @@ void P082_setSystemTime(struct EventStruct *event) {
|
||||
if (updated) {
|
||||
// Use floating point precision to use the time since last update from GPS
|
||||
// and the given offset in centisecond.
|
||||
double time = makeTime(dateTime);
|
||||
time += static_cast<double>(age) / 1000.0;
|
||||
ESPEASY_RULES_FLOAT_TYPE time = makeTime(dateTime);
|
||||
time += (static_cast<ESPEASY_RULES_FLOAT_TYPE>(age) / static_cast<ESPEASY_RULES_FLOAT_TYPE>(1000));
|
||||
node_time.setExternalTimeSource(time, timeSource_t::GPS_time_source);
|
||||
P082_data->_last_setSystemTime = millis();
|
||||
}
|
||||
|
||||
+17
-14
@@ -20,14 +20,14 @@
|
||||
|
||||
#define VEML6070_ADDR_H 0x39
|
||||
#define VEML6070_ADDR_L 0x38
|
||||
#define VEML6070_RSET_DEFAULT 270000 // 270K default resistor value 270000 ohm, range from 220K..1Meg
|
||||
#define VEML6070_UV_MAX_INDEX 15 // normal 11, internal on weather laboratories and NASA it's 15 so far the sensor is linear
|
||||
#define VEML6070_UV_MAX_DEFAULT 11 // 11 = public default table values
|
||||
#define VEML6070_POWER_COEFFCIENT 0.025 // based on calculations from Karel Vanicek and reorder by hand
|
||||
#define VEML6070_TABLE_COEFFCIENT 32.86270591 // calculated by hand with help from a friend of mine, a professor which works in aero space
|
||||
// things
|
||||
// (resistor, differences, power coefficients and official UV index calculations (LAT & LONG
|
||||
// will be added later)
|
||||
#define VEML6070_RSET_DEFAULT 270000 // 270K default resistor value 270000 ohm, range from 220K..1Meg
|
||||
#define VEML6070_UV_MAX_INDEX 15 // normal 11, internal on weather laboratories and NASA it's 15 so far the sensor is linear
|
||||
#define VEML6070_UV_MAX_DEFAULT 11 // 11 = public default table values
|
||||
#define VEML6070_POWER_COEFFCIENT 0.025f // based on calculations from Karel Vanicek and reorder by hand
|
||||
#define VEML6070_TABLE_COEFFCIENT 32.86270591f // calculated by hand with help from a friend of mine, a professor which works in aero space
|
||||
// things
|
||||
// (resistor, differences, power coefficients and official UV index calculations (LAT & LONG
|
||||
// will be added later)
|
||||
|
||||
#define VEML6070_base_value ((VEML6070_RSET_DEFAULT / VEML6070_TABLE_COEFFCIENT) / VEML6070_UV_MAX_DEFAULT) * (1)
|
||||
#define VEML6070_max_value ((VEML6070_RSET_DEFAULT / VEML6070_TABLE_COEFFCIENT) / VEML6070_UV_MAX_DEFAULT) * (VEML6070_UV_MAX_INDEX)
|
||||
@@ -116,7 +116,7 @@ boolean Plugin_084(uint8_t function, struct EventStruct *event, String& string)
|
||||
case PLUGIN_READ:
|
||||
{
|
||||
uint16_t uv_raw;
|
||||
double uv_risk, uv_power;
|
||||
ESPEASY_RULES_FLOAT_TYPE uv_risk, uv_power;
|
||||
bool read_status;
|
||||
|
||||
uv_raw = VEML6070_ReadUv(&read_status); // get UV raw values
|
||||
@@ -183,12 +183,15 @@ bool VEML6070_Init(uint8_t it)
|
||||
// 11.0 - 12.9 "BurnL1/2" = sun->skin burns level 1..2
|
||||
// 13.0 - 25.0 "BurnL3" = sun->skin burns with level 3
|
||||
|
||||
double VEML6070_UvRiskLevel(uint16_t uv_level)
|
||||
ESPEASY_RULES_FLOAT_TYPE VEML6070_UvRiskLevel(uint16_t uv_level)
|
||||
{
|
||||
double risk = 0;
|
||||
ESPEASY_RULES_FLOAT_TYPE risk{};
|
||||
|
||||
if (uv_level < VEML6070_max_value) {
|
||||
return (double)uv_level / VEML6070_base_value;
|
||||
constexpr ESPEASY_RULES_FLOAT_TYPE max_value = VEML6070_max_value;
|
||||
|
||||
if (uv_level < max_value) {
|
||||
constexpr ESPEASY_RULES_FLOAT_TYPE factor = VEML6070_base_value;
|
||||
return (ESPEASY_RULES_FLOAT_TYPE)uv_level / factor;
|
||||
} else {
|
||||
// out of range and much to high - it must be outerspace or sensor damaged
|
||||
if (loglevelActiveFor(LOG_LEVEL_INFO)) {
|
||||
@@ -201,7 +204,7 @@ double VEML6070_UvRiskLevel(uint16_t uv_level)
|
||||
}
|
||||
}
|
||||
|
||||
double VEML6070_UvPower(double uvrisk)
|
||||
ESPEASY_RULES_FLOAT_TYPE VEML6070_UvPower(ESPEASY_RULES_FLOAT_TYPE uvrisk)
|
||||
{
|
||||
// based on calculations for effective irradiation from Karel Vanicek
|
||||
return VEML6070_POWER_COEFFCIENT * uvrisk;
|
||||
|
||||
@@ -304,8 +304,7 @@ boolean Plugin_103(uint8_t function, struct EventStruct *event, String& string)
|
||||
(board_type == AtlasEZO_Sensors_e::EC) ||
|
||||
(board_type == AtlasEZO_Sensors_e::DO))
|
||||
{
|
||||
double value;
|
||||
char strValue[6] = { 0 };
|
||||
ESPEASY_RULES_FLOAT_TYPE value{};
|
||||
|
||||
addFormSubHeader(F("Temperature compensation"));
|
||||
char deviceTemperatureTemplate[40] = { 0 };
|
||||
@@ -324,9 +323,7 @@ boolean Plugin_103(uint8_t function, struct EventStruct *event, String& string)
|
||||
value = P103_FIXED_TEMP_VALUE;
|
||||
}
|
||||
|
||||
dtostrf(value, 5, 2, strValue);
|
||||
ZERO_TERMINATE(strValue);
|
||||
addFormNote(concat(F("Actual value: "), String(strValue)));
|
||||
addFormNote(concat(F("Actual value: "), toString(value, 2)));
|
||||
}
|
||||
|
||||
success = true;
|
||||
@@ -461,7 +458,7 @@ boolean Plugin_103(uint8_t function, struct EventStruct *event, String& string)
|
||||
String temperatureString(parseTemplate(deviceTemperatureTemplateString, 40));
|
||||
|
||||
readCommand = F("RT,");
|
||||
double temperatureReading;
|
||||
ESPEASY_RULES_FLOAT_TYPE temperatureReading{};
|
||||
|
||||
if (Calculate(temperatureString, temperatureReading) != CalculateReturnCode::OK)
|
||||
{
|
||||
|
||||
@@ -75,7 +75,7 @@ const __FlashStringHelper * Command_Rules_Let(struct EventStruct *event, const c
|
||||
|
||||
if (GetArgv(Line, TmpStr1, 3)) {
|
||||
if (event->Par1 >= 0) {
|
||||
double result = 0.0;
|
||||
ESPEASY_RULES_FLOAT_TYPE result{};
|
||||
|
||||
if (!isError(Calculate(TmpStr1, result))) {
|
||||
setCustomFloatVar(event->Par1, result);
|
||||
@@ -86,10 +86,10 @@ const __FlashStringHelper * Command_Rules_Let(struct EventStruct *event, const c
|
||||
return return_command_failed();
|
||||
}
|
||||
|
||||
const __FlashStringHelper * Command_Rules_IncDec(struct EventStruct *event, const char *Line, const double factor)
|
||||
const __FlashStringHelper * Command_Rules_IncDec(struct EventStruct *event, const char *Line, const ESPEASY_RULES_FLOAT_TYPE factor)
|
||||
{
|
||||
String TmpStr1;
|
||||
double result = 1.0;
|
||||
ESPEASY_RULES_FLOAT_TYPE result = 1;
|
||||
|
||||
if (GetArgv(Line, TmpStr1, 3) && isError(Calculate(TmpStr1, result))) {
|
||||
return return_command_failed();
|
||||
|
||||
@@ -131,7 +131,7 @@ const __FlashStringHelper * taskValueSet(struct EventStruct *event, const char *
|
||||
// FIXME TD-er: Must check if the value has to be computed and not convert to double when sensor type is 64 bit int.
|
||||
|
||||
// Perform calculation with float result.
|
||||
double result = 0;
|
||||
ESPEASY_RULES_FLOAT_TYPE result{};
|
||||
|
||||
if (isError(Calculate(TmpStr1, result))) {
|
||||
success = false;
|
||||
|
||||
@@ -2911,7 +2911,7 @@ To create/register a plugin, you have to :
|
||||
// Extra task value types, typically used in Dummy tasks.
|
||||
// For example 32-bit, 64-bit ints and doubles.
|
||||
#ifndef FEATURE_EXTENDED_TASK_VALUE_TYPES
|
||||
#ifdef ESP8266_1M
|
||||
#ifdef LIMIT_BUILD_SIZE
|
||||
#define FEATURE_EXTENDED_TASK_VALUE_TYPES 0
|
||||
#else
|
||||
#define FEATURE_EXTENDED_TASK_VALUE_TYPES 1
|
||||
@@ -2931,5 +2931,21 @@ To create/register a plugin, you have to :
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#ifndef ESPEASY_RULES_FLOAT_TYPE
|
||||
#if defined(ESP8266) && defined(LIMIT_BUILD_SIZE)
|
||||
#ifdef FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
#undef FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
#define FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE 0
|
||||
#endif
|
||||
#define ESPEASY_RULES_FLOAT_TYPE float
|
||||
#else
|
||||
#ifdef FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
#undef FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
#define FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE 1
|
||||
#endif
|
||||
#define ESPEASY_RULES_FLOAT_TYPE double
|
||||
#endif
|
||||
#endif
|
||||
|
||||
|
||||
#endif // CUSTOMBUILD_DEFINE_PLUGIN_SETS_H
|
||||
@@ -238,7 +238,7 @@ bool Modbus::hasTimeout()
|
||||
// tryread can be called in a round robin fashion. It will initiate a read if Modbus is idle and update the result once it is available.
|
||||
// subsequent calls (if Modbus is busy etc. ) will return false and not update the result.
|
||||
// Use to read multiple values non blocking in an re-entrant function. Not tested yet.
|
||||
bool Modbus::tryRead(uint8_t ModbusID, uint16_t M_register, MODBUS_registerTypes_t type, char *IPaddress, double& result) {
|
||||
bool Modbus::tryRead(uint8_t ModbusID, uint16_t M_register, MODBUS_registerTypes_t type, char *IPaddress, ESPEASY_RULES_FLOAT_TYPE& result) {
|
||||
if (isBusy()) { return false; // not done yet
|
||||
}
|
||||
|
||||
|
||||
@@ -21,7 +21,7 @@ public:
|
||||
uint16_t ModbusRegister,
|
||||
MODBUS_registerTypes_t type,
|
||||
char *IPaddress);
|
||||
double read() {
|
||||
ESPEASY_RULES_FLOAT_TYPE read() {
|
||||
if (resultReceived) {
|
||||
resultReceived = false;
|
||||
return result;
|
||||
@@ -48,34 +48,34 @@ public:
|
||||
handle();
|
||||
}
|
||||
|
||||
bool tryRead(uint8_t ModbusID,
|
||||
uint16_t M_register,
|
||||
MODBUS_registerTypes_t type,
|
||||
char *IPaddress,
|
||||
double & result);
|
||||
bool tryRead(uint8_t ModbusID,
|
||||
uint16_t M_register,
|
||||
MODBUS_registerTypes_t type,
|
||||
char *IPaddress,
|
||||
ESPEASY_RULES_FLOAT_TYPE& result);
|
||||
|
||||
private:
|
||||
|
||||
WiFiClient *ModbusClient = nullptr; // pointer to tcp client
|
||||
unsigned int errcnt = 0;
|
||||
char sendBuffer[12] = { 0, 1, 0, 0, 0, 6, 0x7e, 4, 0x9d, 7, 0, 1 };
|
||||
#ifndef BUILD_NO_DEBUG
|
||||
String LogString; // for debug logging
|
||||
#endif
|
||||
unsigned long timeout = 0; // send and read timeout
|
||||
MODBUS_states_t TXRXstate = MODBUS_IDLE; // state for handle() state machine
|
||||
unsigned int RXavailable = 0;
|
||||
unsigned int payLoad = 0; // number of bytes to receive as payload. Payload may come as seperate frame.
|
||||
WiFiClient *ModbusClient = nullptr; // pointer to tcp client
|
||||
unsigned int errcnt = 0;
|
||||
char sendBuffer[12] = { 0, 1, 0, 0, 0, 6, 0x7e, 4, 0x9d, 7, 0, 1 };
|
||||
# ifndef BUILD_NO_DEBUG
|
||||
String LogString; // for debug logging
|
||||
# endif // ifndef BUILD_NO_DEBUG
|
||||
unsigned long timeout = 0; // send and read timeout
|
||||
MODBUS_states_t TXRXstate = MODBUS_IDLE; // state for handle() state machine
|
||||
unsigned int RXavailable = 0;
|
||||
unsigned int payLoad = 0; // number of bytes to receive as payload. Payload may come as seperate frame.
|
||||
bool hasTimeout();
|
||||
MODBUS_registerTypes_t incomingValue = signed16; // how to interpret the incoming value
|
||||
double result = 0.0; // incoming value, converted to double
|
||||
bool resultReceived = false; // incoming value is valid ?
|
||||
ESPEASY_RULES_FLOAT_TYPE result{}; // incoming value, converted to ESPEASY_RULES_FLOAT_TYPE
|
||||
bool resultReceived = false; // incoming value is valid ?
|
||||
bool isBusy(void) {
|
||||
return TXRXstate != MODBUS_IDLE;
|
||||
}
|
||||
|
||||
uint16_t currentRegister = 0;
|
||||
uint8_t currentFunction = 0;
|
||||
uint8_t currentFunction = 0;
|
||||
};
|
||||
|
||||
|
||||
|
||||
@@ -304,7 +304,7 @@ bool PluginStats::webformLoad_show_peaks(struct EventStruct *event, bool include
|
||||
void PluginStats::webformLoad_show_val(
|
||||
struct EventStruct *event,
|
||||
const String & label,
|
||||
double value,
|
||||
ESPEASY_RULES_FLOAT_TYPE value,
|
||||
const String & unit) const
|
||||
{
|
||||
addRowLabel(getLabel() + label);
|
||||
|
||||
@@ -107,7 +107,7 @@ public:
|
||||
void webformLoad_show_val(
|
||||
struct EventStruct *event,
|
||||
const String & label,
|
||||
double value,
|
||||
ESPEASY_RULES_FLOAT_TYPE value,
|
||||
const String & unit) const;
|
||||
|
||||
|
||||
|
||||
@@ -156,7 +156,7 @@ void UserVarStruct::setFloat(taskIndex_t taskIndex,
|
||||
}
|
||||
|
||||
#if FEATURE_EXTENDED_TASK_VALUE_TYPES
|
||||
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
double UserVarStruct::getDouble(taskIndex_t taskIndex,
|
||||
uint8_t varNr) const
|
||||
{
|
||||
@@ -174,10 +174,10 @@ void UserVarStruct::setDouble(taskIndex_t taskIndex,
|
||||
_data[taskIndex].setDouble(varNr, value);
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
#endif // if FEATURE_EXTENDED_TASK_VALUE_TYPES
|
||||
|
||||
double UserVarStruct::getAsDouble(taskIndex_t taskIndex,
|
||||
ESPEASY_RULES_FLOAT_TYPE UserVarStruct::getAsDouble(taskIndex_t taskIndex,
|
||||
uint8_t varNr,
|
||||
Sensor_VType sensorType) const
|
||||
{
|
||||
@@ -195,7 +195,7 @@ String UserVarStruct::getAsString(taskIndex_t taskIndex, uint8_t varNr, Sensor_V
|
||||
return EMPTY_STRING;
|
||||
}
|
||||
|
||||
void UserVarStruct::set(taskIndex_t taskIndex, uint8_t varNr, const double& value, Sensor_VType sensorType)
|
||||
void UserVarStruct::set(taskIndex_t taskIndex, uint8_t varNr, const ESPEASY_RULES_FLOAT_TYPE& value, Sensor_VType sensorType)
|
||||
{
|
||||
if (taskIndex < _data.size()) {
|
||||
_data[taskIndex].set(varNr, value, sensorType);
|
||||
|
||||
@@ -65,16 +65,17 @@ struct UserVarStruct {
|
||||
float value);
|
||||
|
||||
#if FEATURE_EXTENDED_TASK_VALUE_TYPES
|
||||
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
// Double stored at the memory location of the float
|
||||
double getDouble(taskIndex_t taskIndex,
|
||||
uint8_t varNr) const;
|
||||
void setDouble(taskIndex_t taskIndex,
|
||||
uint8_t varNr,
|
||||
double value);
|
||||
#endif
|
||||
#endif // if FEATURE_EXTENDED_TASK_VALUE_TYPES
|
||||
|
||||
double getAsDouble(taskIndex_t taskIndex,
|
||||
ESPEASY_RULES_FLOAT_TYPE getAsDouble(taskIndex_t taskIndex,
|
||||
uint8_t varNr,
|
||||
Sensor_VType sensorType) const;
|
||||
|
||||
@@ -86,7 +87,7 @@ struct UserVarStruct {
|
||||
|
||||
void set(taskIndex_t taskIndex,
|
||||
uint8_t varNr,
|
||||
const double& value,
|
||||
const ESPEASY_RULES_FLOAT_TYPE& value,
|
||||
Sensor_VType sensorType);
|
||||
|
||||
bool isValid(taskIndex_t taskIndex,
|
||||
|
||||
@@ -48,9 +48,11 @@ Web_StreamingBuffer& Web_StreamingBuffer::operator+=(const float& a) {
|
||||
return addString(toString(a, 2));
|
||||
}
|
||||
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
Web_StreamingBuffer& Web_StreamingBuffer::operator+=(const double& a) {
|
||||
return addString(doubleToString(a));
|
||||
}
|
||||
#endif
|
||||
|
||||
Web_StreamingBuffer& Web_StreamingBuffer::operator+=(const String& a) {
|
||||
return addString(a);
|
||||
|
||||
@@ -41,7 +41,9 @@ public:
|
||||
Web_StreamingBuffer& operator+=(int64_t a);
|
||||
|
||||
Web_StreamingBuffer& operator+=(const float& a);
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
Web_StreamingBuffer& operator+=(const double& a);
|
||||
#endif
|
||||
|
||||
template <typename T>
|
||||
Web_StreamingBuffer& operator+=(T a) {
|
||||
|
||||
@@ -18,7 +18,7 @@ uint8_t getValueCountFromSensorType(Sensor_VType sensorType)
|
||||
case Sensor_VType::SENSOR_TYPE_INT32_SINGLE: // 1x int32_t
|
||||
case Sensor_VType::SENSOR_TYPE_UINT64_SINGLE: // 1x uint64_t
|
||||
case Sensor_VType::SENSOR_TYPE_INT64_SINGLE: // 1x int64_t
|
||||
case Sensor_VType::SENSOR_TYPE_DOUBLE_SINGLE: // 1x double
|
||||
case Sensor_VType::SENSOR_TYPE_DOUBLE_SINGLE: // 1x ESPEASY_RULES_FLOAT_TYPE
|
||||
#endif
|
||||
case Sensor_VType::SENSOR_TYPE_SWITCH:
|
||||
case Sensor_VType::SENSOR_TYPE_DIMMER:
|
||||
@@ -33,7 +33,7 @@ uint8_t getValueCountFromSensorType(Sensor_VType sensorType)
|
||||
case Sensor_VType::SENSOR_TYPE_INT32_DUAL: // 2x int32_t
|
||||
case Sensor_VType::SENSOR_TYPE_UINT64_DUAL: // 2x uint64_t
|
||||
case Sensor_VType::SENSOR_TYPE_INT64_DUAL: // 2x int64_t
|
||||
case Sensor_VType::SENSOR_TYPE_DOUBLE_DUAL: // 2x double
|
||||
case Sensor_VType::SENSOR_TYPE_DOUBLE_DUAL: // 2x ESPEASY_RULES_FLOAT_TYPE
|
||||
#endif
|
||||
return 2;
|
||||
case Sensor_VType::SENSOR_TYPE_TEMP_HUM_BARO:
|
||||
|
||||
@@ -138,7 +138,7 @@ void TaskValues_Data_t::setFloat(uint8_t varNr, float value)
|
||||
}
|
||||
|
||||
#if FEATURE_EXTENDED_TASK_VALUE_TYPES
|
||||
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
double TaskValues_Data_t::getDouble(uint8_t varNr) const
|
||||
{
|
||||
if ((varNr < (VARS_PER_TASK / 2))) {
|
||||
@@ -154,8 +154,9 @@ void TaskValues_Data_t::setDouble(uint8_t varNr, double value)
|
||||
}
|
||||
}
|
||||
#endif
|
||||
#endif
|
||||
|
||||
double TaskValues_Data_t::getAsDouble(uint8_t varNr, Sensor_VType sensorType) const
|
||||
ESPEASY_RULES_FLOAT_TYPE TaskValues_Data_t::getAsDouble(uint8_t varNr, Sensor_VType sensorType) const
|
||||
{
|
||||
if (sensorType == Sensor_VType::SENSOR_TYPE_ULONG) {
|
||||
return getSensorTypeLong();
|
||||
@@ -170,14 +171,16 @@ double TaskValues_Data_t::getAsDouble(uint8_t varNr, Sensor_VType sensorType) co
|
||||
return getUint64(varNr);
|
||||
} else if (isInt64OutputDataType(sensorType)) {
|
||||
return getInt64(varNr);
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
} else if (isDoubleOutputDataType(sensorType)) {
|
||||
return getDouble(varNr);
|
||||
#endif
|
||||
#endif
|
||||
}
|
||||
return 0.0;
|
||||
}
|
||||
|
||||
void TaskValues_Data_t::set(uint8_t varNr, const double& value, Sensor_VType sensorType)
|
||||
void TaskValues_Data_t::set(uint8_t varNr, const ESPEASY_RULES_FLOAT_TYPE& value, Sensor_VType sensorType)
|
||||
{
|
||||
if (sensorType == Sensor_VType::SENSOR_TYPE_ULONG) {
|
||||
// Legacy formatting the old "SENSOR_TYPE_ULONG" type
|
||||
@@ -193,8 +196,10 @@ void TaskValues_Data_t::set(uint8_t varNr, const double& value, Sensor_VType sen
|
||||
setUint64(varNr, value);
|
||||
} else if (isInt64OutputDataType(sensorType)) {
|
||||
setInt64(varNr, value);
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
} else if (isDoubleOutputDataType(sensorType)) {
|
||||
setDouble(varNr, value);
|
||||
#endif
|
||||
#endif
|
||||
}
|
||||
}
|
||||
@@ -206,8 +211,10 @@ bool TaskValues_Data_t::isValid(uint8_t varNr, Sensor_VType sensorType) const
|
||||
} else if (isFloatOutputDataType(sensorType)) {
|
||||
return isValidFloat(getFloat(varNr));
|
||||
#if FEATURE_EXTENDED_TASK_VALUE_TYPES
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
} else if (isDoubleOutputDataType(sensorType)) {
|
||||
return isValidDouble(getDouble(varNr));
|
||||
#endif
|
||||
#endif
|
||||
}
|
||||
return true;
|
||||
@@ -220,8 +227,10 @@ String TaskValues_Data_t::getAsString(uint8_t varNr, Sensor_VType sensorType, u
|
||||
if (isFloatOutputDataType(sensorType)) {
|
||||
result = toString(getFloat(varNr), nrDecimals);
|
||||
#if FEATURE_EXTENDED_TASK_VALUE_TYPES
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
} else if (isDoubleOutputDataType(sensorType)) {
|
||||
result = doubleToString(getDouble(varNr), nrDecimals);
|
||||
#endif
|
||||
#endif
|
||||
} else if (sensorType == Sensor_VType::SENSOR_TYPE_ULONG) {
|
||||
return String(getSensorTypeLong());
|
||||
|
||||
@@ -45,18 +45,19 @@ struct TaskValues_Data_t {
|
||||
float value);
|
||||
|
||||
#if FEATURE_EXTENDED_TASK_VALUE_TYPES
|
||||
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
double getDouble(uint8_t varNr) const;
|
||||
void setDouble(uint8_t varNr,
|
||||
double value);
|
||||
#endif
|
||||
#endif
|
||||
|
||||
// Interpret the data according to the given sensorType
|
||||
double getAsDouble(uint8_t varNr,
|
||||
ESPEASY_RULES_FLOAT_TYPE getAsDouble(uint8_t varNr,
|
||||
Sensor_VType sensorType) const;
|
||||
|
||||
void set(uint8_t varNr,
|
||||
const double& value,
|
||||
const ESPEASY_RULES_FLOAT_TYPE& value,
|
||||
Sensor_VType sensorType);
|
||||
|
||||
bool isValid(uint8_t varNr,
|
||||
@@ -73,7 +74,9 @@ struct TaskValues_Data_t {
|
||||
int32_t int32s[VARS_PER_TASK];
|
||||
uint64_t uint64s[VARS_PER_TASK / 2];
|
||||
int64_t int64s[VARS_PER_TASK / 2];
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
double doubles[VARS_PER_TASK / 2];
|
||||
#endif
|
||||
#endif
|
||||
};
|
||||
};
|
||||
|
||||
@@ -675,7 +675,7 @@ void SensorSendTask(struct EventStruct *event, unsigned long timestampUnixTime,
|
||||
// See: https://github.com/letscontrolit/ESPEasy/issues/3721#issuecomment-889649437
|
||||
formula.replace(F("%pvalue%"), preValue[varNr]);
|
||||
formula.replace(F("%value%"), formatUserVarNoCheck(&TempEvent, varNr));
|
||||
double result = 0;
|
||||
ESPEASY_RULES_FLOAT_TYPE result{};
|
||||
|
||||
if (!isError(Calculate(parseTemplate(formula), result))) {
|
||||
UserVar.set(event->TaskIndex, varNr, result, TempEvent.sensorType);
|
||||
|
||||
@@ -424,8 +424,8 @@ bool parse_bitwise_functions(const String& cmd_s_lower, const String& arg1, cons
|
||||
return true;
|
||||
}
|
||||
|
||||
bool parse_math_functions(const String& cmd_s_lower, const String& arg1, const String& arg2, const String& arg3, double& result) {
|
||||
double farg1;
|
||||
bool parse_math_functions(const String& cmd_s_lower, const String& arg1, const String& arg2, const String& arg3, ESPEASY_RULES_FLOAT_TYPE& result) {
|
||||
ESPEASY_RULES_FLOAT_TYPE farg1;
|
||||
float farg2, farg3 = 0.0f;
|
||||
|
||||
if (!validDoubleFromString(arg1, farg1)) {
|
||||
@@ -486,7 +486,7 @@ void parse_string_commands(String& line) {
|
||||
if (cmd_s_lower.length() > 0) {
|
||||
String replacement; // maybe just replace with empty to avoid looping?
|
||||
uint64_t iarg1, iarg2 = 0;
|
||||
double fresult = 0.0;
|
||||
ESPEASY_RULES_FLOAT_TYPE fresult{};
|
||||
int64_t iresult = 0;
|
||||
int startpos, endpos = -1;
|
||||
const bool arg1valid = validIntFromString(arg1, startpos);
|
||||
@@ -494,7 +494,11 @@ void parse_string_commands(String& line) {
|
||||
|
||||
if (parse_math_functions(cmd_s_lower, arg1, arg2, arg3, fresult)) {
|
||||
const bool trimTrailingZeros = true;
|
||||
replacement = doubleToString(fresult, maxNrDecimals_double(fresult), trimTrailingZeros);
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
replacement = doubleToString(fresult, maxNrDecimals_fpType(fresult), trimTrailingZeros);
|
||||
#else
|
||||
replacement = floatToString(fresult, maxNrDecimals_fpType(fresult), trimTrailingZeros);
|
||||
#endif
|
||||
} else if (parse_bitwise_functions(cmd_s_lower, arg1, arg2, arg3, iresult)) {
|
||||
replacement = ull2String(iresult);
|
||||
} else {
|
||||
@@ -1209,8 +1213,8 @@ bool conditionMatch(const String& check) {
|
||||
|
||||
tmpCheck1.trim();
|
||||
tmpCheck2.trim();
|
||||
double Value1 = 0;
|
||||
double Value2 = 0;
|
||||
ESPEASY_RULES_FLOAT_TYPE Value1{};
|
||||
ESPEASY_RULES_FLOAT_TYPE Value2{};
|
||||
|
||||
int timeInSec1 = 0;
|
||||
int timeInSec2 = 0;
|
||||
@@ -1267,9 +1271,19 @@ bool conditionMatch(const String& check) {
|
||||
|
||||
log += '(';
|
||||
const bool trimTrailingZeros = true;
|
||||
log += compareTimes ? String(timeInSec1) : doubleToString(Value1, 6, trimTrailingZeros);
|
||||
log += compareTimes ? String(timeInSec1) :
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
doubleToString(Value1, 6, trimTrailingZeros);
|
||||
#else
|
||||
floatToString(Value1, 6, trimTrailingZeros);
|
||||
#endif
|
||||
log += wrap_String(check.substring(posStart, posEnd), ' '); // Compare
|
||||
log += compareTimes ? String(timeInSec2) : doubleToString(Value2, 6, trimTrailingZeros);
|
||||
log += compareTimes ? String(timeInSec2) :
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
doubleToString(Value2, 6, trimTrailingZeros);
|
||||
#else
|
||||
floatToString(Value2, 6, trimTrailingZeros);
|
||||
#endif
|
||||
log += ')';
|
||||
addLogMove(LOG_LEVEL_DEBUG, log);
|
||||
}
|
||||
|
||||
@@ -61,7 +61,7 @@ bool parse_math_functions(const String& cmd_s_lower,
|
||||
const String& arg1,
|
||||
const String& arg2,
|
||||
const String& arg3,
|
||||
double & result);
|
||||
ESPEASY_RULES_FLOAT_TYPE & result);
|
||||
|
||||
void parse_string_commands(String& line);
|
||||
|
||||
|
||||
@@ -17,7 +17,7 @@ int CalculateParam(const String& TmpStr) {
|
||||
if (TmpStr[0] != '=') {
|
||||
validIntFromString(TmpStr, returnValue);
|
||||
} else {
|
||||
double param = 0;
|
||||
ESPEASY_RULES_FLOAT_TYPE param{};
|
||||
|
||||
// Starts with an '=', so Calculate starting at next position
|
||||
CalculateReturnCode returnCode = Calculate(TmpStr.substring(1), param);
|
||||
@@ -40,7 +40,7 @@ int CalculateParam(const String& TmpStr) {
|
||||
}
|
||||
|
||||
CalculateReturnCode Calculate(const String& input,
|
||||
double & result)
|
||||
ESPEASY_RULES_FLOAT_TYPE & result)
|
||||
{
|
||||
START_TIMER;
|
||||
CalculateReturnCode returnCode = RulesCalculate.doCalculate(
|
||||
@@ -78,7 +78,11 @@ CalculateReturnCode Calculate(const String& input,
|
||||
log += F(" = ");
|
||||
|
||||
const bool trimTrailingZeros = true;
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
log += doubleToString(result, 6, trimTrailingZeros);
|
||||
#else
|
||||
log += floatToString(result, 6, trimTrailingZeros);
|
||||
#endif
|
||||
#endif // ifndef BUILD_NO_DEBUG
|
||||
|
||||
addLogMove(LOG_LEVEL_ERROR, log);
|
||||
|
||||
@@ -20,7 +20,7 @@ extern RulesCalculate_t RulesCalculate;
|
||||
int CalculateParam(const String& TmpStr);
|
||||
|
||||
CalculateReturnCode Calculate(const String& input,
|
||||
double & result);
|
||||
ESPEASY_RULES_FLOAT_TYPE & result);
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -1,14 +1,14 @@
|
||||
#include "../Globals/RuntimeData.h"
|
||||
|
||||
|
||||
std::map<uint32_t, double> customFloatVar;
|
||||
std::map<uint32_t, ESPEASY_RULES_FLOAT_TYPE> customFloatVar;
|
||||
|
||||
//float UserVar[VARS_PER_TASK * TASKS_MAX];
|
||||
|
||||
UserVarStruct UserVar;
|
||||
|
||||
|
||||
double getCustomFloatVar(uint32_t index) {
|
||||
ESPEASY_RULES_FLOAT_TYPE getCustomFloatVar(uint32_t index) {
|
||||
auto it = customFloatVar.find(index);
|
||||
|
||||
if (it != customFloatVar.end()) {
|
||||
@@ -17,11 +17,11 @@ double getCustomFloatVar(uint32_t index) {
|
||||
return 0.0;
|
||||
}
|
||||
|
||||
void setCustomFloatVar(uint32_t index, const double& value) {
|
||||
void setCustomFloatVar(uint32_t index, const ESPEASY_RULES_FLOAT_TYPE& value) {
|
||||
customFloatVar[index] = value;
|
||||
}
|
||||
|
||||
bool getNextCustomFloatVar(uint32_t& index, double& value) {
|
||||
bool getNextCustomFloatVar(uint32_t& index, ESPEASY_RULES_FLOAT_TYPE& value) {
|
||||
auto it = customFloatVar.find(index);
|
||||
|
||||
if (it == customFloatVar.end()) { return false; }
|
||||
|
||||
@@ -17,12 +17,12 @@
|
||||
* let,1,10
|
||||
* if %v1%=10 do ...
|
||||
\*********************************************************************************************/
|
||||
extern std::map<uint32_t, double> customFloatVar;
|
||||
extern std::map<uint32_t, ESPEASY_RULES_FLOAT_TYPE> customFloatVar;
|
||||
|
||||
double getCustomFloatVar(uint32_t index);
|
||||
void setCustomFloatVar(uint32_t index, const double& value);
|
||||
ESPEASY_RULES_FLOAT_TYPE getCustomFloatVar(uint32_t index);
|
||||
void setCustomFloatVar(uint32_t index, const ESPEASY_RULES_FLOAT_TYPE& value);
|
||||
|
||||
bool getNextCustomFloatVar(uint32_t& index, double& value);
|
||||
bool getNextCustomFloatVar(uint32_t& index, ESPEASY_RULES_FLOAT_TYPE& value);
|
||||
|
||||
|
||||
/*********************************************************************************************\
|
||||
|
||||
@@ -5,14 +5,15 @@
|
||||
// See: https://github.com/esp8266/Arduino/issues/8922#issuecomment-1542301697
|
||||
#include <cmath>
|
||||
|
||||
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
double ESPEASY_DOUBLE_EPSILON = ESPEASY_DOUBLE_EPSILON_FACTOR * std::numeric_limits<double>::epsilon();
|
||||
double ESPEASY_DOUBLE_EPSILON_NEG = -1.0 * ESPEASY_DOUBLE_EPSILON_FACTOR * std::numeric_limits<double>::epsilon();
|
||||
#endif
|
||||
float ESPEASY_FLOAT_EPSILON = std::numeric_limits<float>::epsilon();
|
||||
float ESPEASY_FLOAT_EPSILON_NEG = -1.0f * std::numeric_limits<float>::epsilon();
|
||||
|
||||
|
||||
int maxNrDecimals_double(const double& value)
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
int maxNrDecimals_fpType(const double& value)
|
||||
{
|
||||
int res = ESPEASY_DOUBLE_NR_DECIMALS;
|
||||
double factor = 1;
|
||||
@@ -23,91 +24,184 @@ int maxNrDecimals_double(const double& value)
|
||||
}
|
||||
return res;
|
||||
}
|
||||
#endif
|
||||
int maxNrDecimals_fpType(const float& value)
|
||||
{
|
||||
int res = ESPEASY_FLOAT_NR_DECIMALS;
|
||||
float factor = 1;
|
||||
|
||||
while ((value / factor) > 10 && res > 2) {
|
||||
factor *= 10.0f;
|
||||
--res;
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
bool approximatelyEqual(const double& a, const double& b) {
|
||||
return approximatelyEqual(a, b, ESPEASY_DOUBLE_EPSILON);
|
||||
}
|
||||
#endif
|
||||
|
||||
bool approximatelyEqual(const float& a, const float& b) {
|
||||
return approximatelyEqual(a, b, ESPEASY_FLOAT_EPSILON);
|
||||
}
|
||||
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
bool approximatelyEqual(const double& a, const double& b, double epsilon)
|
||||
{
|
||||
return std::abs(a - b) <= ((std::abs(a) < std::abs(b) ? std::abs(b) : std::abs(a)) * epsilon);
|
||||
}
|
||||
#endif
|
||||
|
||||
bool approximatelyEqual(const float& a, const float& b, float epsilon)
|
||||
{
|
||||
return std::abs(a - b) <= ((std::abs(a) < std::abs(b) ? std::abs(b) : std::abs(a)) * epsilon);
|
||||
}
|
||||
|
||||
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
bool definitelyGreaterThan(const double& a, const double& b) {
|
||||
return definitelyGreaterThan(a, b, ESPEASY_DOUBLE_EPSILON);
|
||||
}
|
||||
#endif
|
||||
|
||||
bool definitelyGreaterThan(const float& a, const float& b) {
|
||||
return definitelyGreaterThan(a, b, ESPEASY_FLOAT_EPSILON);
|
||||
}
|
||||
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
bool definitelyGreaterThan(const double& a, const double& b, double epsilon)
|
||||
{
|
||||
return (a - b) > ((std::abs(a) < std::abs(b) ? std::abs(b) : std::abs(a)) * epsilon);
|
||||
}
|
||||
#endif
|
||||
|
||||
bool definitelyGreaterThan(const float& a, const float& b, float epsilon)
|
||||
{
|
||||
return (a - b) > ((std::abs(a) < std::abs(b) ? std::abs(b) : std::abs(a)) * epsilon);
|
||||
}
|
||||
|
||||
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
bool definitelyLessThan(const double& a, const double& b) {
|
||||
return definitelyLessThan(a, b, ESPEASY_DOUBLE_EPSILON);
|
||||
}
|
||||
#endif
|
||||
|
||||
bool definitelyLessThan(const float& a, const float& b) {
|
||||
return definitelyLessThan(a, b, ESPEASY_FLOAT_EPSILON);
|
||||
}
|
||||
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
bool definitelyLessThan(const double& a, const double& b, double epsilon)
|
||||
{
|
||||
return (b - a) > ((std::abs(a) < std::abs(b) ? std::abs(b) : std::abs(a)) * epsilon);
|
||||
}
|
||||
#endif
|
||||
|
||||
bool definitelyLessThan(const float& a, const float& b, float epsilon)
|
||||
{
|
||||
return (b - a) > ((std::abs(a) < std::abs(b) ? std::abs(b) : std::abs(a)) * epsilon);
|
||||
}
|
||||
|
||||
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
bool essentiallyEqual(const double& a, const double& b) {
|
||||
return essentiallyEqual(a, b, ESPEASY_DOUBLE_EPSILON);
|
||||
}
|
||||
#endif
|
||||
|
||||
bool essentiallyEqual(const float& a, const float& b) {
|
||||
return essentiallyEqual(a, b, ESPEASY_FLOAT_EPSILON);
|
||||
}
|
||||
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
bool essentiallyEqual(const double& a, const double& b, double epsilon)
|
||||
{
|
||||
return std::abs(a - b) <= ((std::abs(a) > std::abs(b) ? std::abs(b) : std::abs(a)) * epsilon);
|
||||
}
|
||||
#endif
|
||||
|
||||
bool essentiallyEqual(const float& a, const float& b, float epsilon)
|
||||
{
|
||||
return std::abs(a - b) <= ((std::abs(a) > std::abs(b) ? std::abs(b) : std::abs(a)) * epsilon);
|
||||
}
|
||||
|
||||
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
bool essentiallyZero(const double& a)
|
||||
{
|
||||
return ESPEASY_DOUBLE_EPSILON_NEG <= a &&
|
||||
a <= ESPEASY_DOUBLE_EPSILON;
|
||||
}
|
||||
#endif
|
||||
|
||||
bool essentiallyZero(const float& a)
|
||||
{
|
||||
return ESPEASY_FLOAT_EPSILON_NEG <= a &&
|
||||
a <= ESPEASY_FLOAT_EPSILON;
|
||||
}
|
||||
|
||||
/*========================================================================*/
|
||||
/* Functions that would otherwise duplicate code */
|
||||
/* For example due to being implemented as macros */
|
||||
/* Or duplications as it is being implemented both for double and float */
|
||||
/*========================================================================*/
|
||||
|
||||
|
||||
float powf(const float x, const float y)
|
||||
{
|
||||
return (float)(pow((double)x, (double)y));
|
||||
}
|
||||
|
||||
float ceilf(const float x)
|
||||
{
|
||||
return (float)(ceil((double)x));
|
||||
}
|
||||
|
||||
float floorf(const float x)
|
||||
{
|
||||
return (float)(floor((double)x));
|
||||
}
|
||||
|
||||
float fabsf(const float x)
|
||||
{
|
||||
return (float)(fabs((double)x));
|
||||
}
|
||||
|
||||
float acosf(const float x)
|
||||
{
|
||||
return (float)(acos((double)x));
|
||||
}
|
||||
|
||||
float cosf(const float x)
|
||||
{
|
||||
return (float)(cos((double)x));
|
||||
}
|
||||
|
||||
float asinf(const float x)
|
||||
{
|
||||
return (float)(asin((double)x));
|
||||
}
|
||||
|
||||
float sinf(const float x)
|
||||
{
|
||||
return (float)(sin((double)x));
|
||||
}
|
||||
|
||||
float atanf(const float x)
|
||||
{
|
||||
return (float)(atan((double)x));
|
||||
}
|
||||
|
||||
float tanf(const float x)
|
||||
{
|
||||
return (float)(tan((double)x));
|
||||
}
|
||||
|
||||
float sqrtf(const float x)
|
||||
{
|
||||
return (float)(sqrt((double)x));
|
||||
}
|
||||
|
||||
float roundf(const float x)
|
||||
{
|
||||
return (float)(round((double)x));
|
||||
}
|
||||
|
||||
@@ -7,33 +7,77 @@
|
||||
// Internal ESPEasy representation of double values
|
||||
#define ESPEASY_DOUBLE_NR_DECIMALS 14
|
||||
#define ESPEASY_DOUBLE_EPSILON_FACTOR 1000
|
||||
#define ESPEASY_FLOAT_NR_DECIMALS 6
|
||||
#define ESPEASY_FLOAT_EPSILON_FACTOR 1000
|
||||
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
int maxNrDecimals_fpType(const double& value);
|
||||
#endif
|
||||
int maxNrDecimals_fpType(const float& value);
|
||||
|
||||
int maxNrDecimals_double(const double& value);
|
||||
|
||||
// The following definitions are from The art of computer programming by Knuth
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
bool approximatelyEqual(const double& a, const double& b);
|
||||
#endif
|
||||
bool approximatelyEqual(const float& a, const float& b);
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
bool approximatelyEqual(const double& a, const double& b, double epsilon);
|
||||
#endif
|
||||
bool approximatelyEqual(const float& a, const float& b, float epsilon);
|
||||
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
bool definitelyGreaterThan(const double& a, const double& b);
|
||||
#endif
|
||||
bool definitelyGreaterThan(const float& a, const float& b);
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
bool definitelyGreaterThan(const double& a, const double& b, double epsilon);
|
||||
#endif
|
||||
bool definitelyGreaterThan(const float& a, const float& b, float epsilon);
|
||||
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
bool definitelyLessThan(const double& a, const double& b);
|
||||
#endif
|
||||
bool definitelyLessThan(const float& a, const float& b);
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
bool definitelyLessThan(const double& a, const double& b, double epsilon);
|
||||
#endif
|
||||
bool definitelyLessThan(const float& a, const float& b, float epsilon);
|
||||
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
bool essentiallyEqual(const double& a, const double& b);
|
||||
#endif
|
||||
bool essentiallyEqual(const float& a, const float& b);
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
bool essentiallyEqual(const double& a, const double& b, double epsilon);
|
||||
#endif
|
||||
bool essentiallyEqual(const float& a, const float& b, float epsilon);
|
||||
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
bool essentiallyZero(const double& a);
|
||||
#endif
|
||||
bool essentiallyZero(const float& a);
|
||||
|
||||
|
||||
/*========================================================================*/
|
||||
/* Functions that would otherwise duplicate code */
|
||||
/* For example due to being implemented as macros */
|
||||
/* Or duplications as it is being implemented both for double and float */
|
||||
/* Another factor is that converting from double to float on each call */
|
||||
/* also adds up */
|
||||
/*========================================================================*/
|
||||
|
||||
float powf(const float x, const float y);
|
||||
float ceilf(const float x);
|
||||
float floorf(const float x);
|
||||
float fabsf(const float x);
|
||||
float acosf(const float x);
|
||||
float cosf(const float x);
|
||||
float asinf(const float x);
|
||||
float sinf(const float x);
|
||||
float atanf(const float x);
|
||||
float tanf(const float x);
|
||||
float sqrtf(const float x);
|
||||
float roundf(const float x);
|
||||
|
||||
#endif // HELPERS_ESPEASY_MATH_H
|
||||
@@ -263,14 +263,18 @@ unsigned long ESPEasy_time::now() {
|
||||
|
||||
if (loglevelActiveFor(LOG_LEVEL_INFO)) {
|
||||
String log = F("Time set to ");
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
log += doubleToString(unixTime_d, 3);
|
||||
#else
|
||||
log += static_cast<uint32_t>(unixTime_d);
|
||||
#endif
|
||||
|
||||
if ((-86400 < time_offset) && (time_offset < 86400)) {
|
||||
// Only useful to show adjustment if it is less than a day.
|
||||
log += F(" Time adjusted by ");
|
||||
log += doubleToString(time_offset * 1000.0);
|
||||
log += static_cast<uint32_t>(time_offset * 1000.0);
|
||||
log += F(" msec. Wander: ");
|
||||
log += doubleToString(timeWander, 1);
|
||||
log += floatToString(timeWander, 1);
|
||||
log += F(" ppm");
|
||||
log += F(" Source: ");
|
||||
log += toString(timeSource);
|
||||
@@ -528,8 +532,8 @@ bool ESPEasy_time::getNtpTime(double& unixTime_d)
|
||||
// We gained more than 1 second in accuracy
|
||||
fractpart += 1.0;
|
||||
}
|
||||
log += doubleToString(fractpart, 3);
|
||||
log += F(" seconds");
|
||||
log += static_cast<int>(fractpart * 1000.0);
|
||||
log += F(" msec");
|
||||
addLogMove(LOG_LEVEL_INFO, log);
|
||||
}
|
||||
udp.stop();
|
||||
|
||||
@@ -10,7 +10,7 @@ bool isValidFloat(float f) {
|
||||
return !isnan(f) && !isinf(f);
|
||||
}
|
||||
|
||||
bool isValidDouble(double f) {
|
||||
bool isValidDouble(ESPEASY_RULES_FLOAT_TYPE f) {
|
||||
return !isnan(f) && !isinf(f);
|
||||
}
|
||||
|
||||
@@ -97,8 +97,8 @@ bool validUInt64FromString(const String& tBuf, uint64_t& result) {
|
||||
|
||||
bool validFloatFromString(const String& tBuf, float& result) {
|
||||
// DO not call validDoubleFromString and then cast to float.
|
||||
// Working with double values is quite CPU intensive as it must be done in software
|
||||
// since the ESP does not have large enough registers for handling double values in hardware.
|
||||
// Working with ESPEASY_RULES_FLOAT_TYPE values is quite CPU intensive as it must be done in software
|
||||
// since the ESP does not have large enough registers for handling ESPEASY_RULES_FLOAT_TYPE values in hardware.
|
||||
NumericalType detectedType;
|
||||
const String numerical = getNumerical(tBuf, NumericalType::FloatingPoint, detectedType);
|
||||
|
||||
@@ -118,7 +118,7 @@ bool validFloatFromString(const String& tBuf, float& result) {
|
||||
return isvalid;
|
||||
}
|
||||
|
||||
bool validDoubleFromString(const String& tBuf, double& result) {
|
||||
bool validDoubleFromString(const String& tBuf, ESPEASY_RULES_FLOAT_TYPE& result) {
|
||||
#if defined(CORE_POST_2_5_0) || defined(ESP32)
|
||||
|
||||
// String.toDouble() is introduced in core 2.5.0
|
||||
@@ -129,7 +129,7 @@ bool validDoubleFromString(const String& tBuf, double& result) {
|
||||
(detectedType == NumericalType::HexadecimalUInt)) {
|
||||
uint64_t tmp;
|
||||
bool isvalid = validUInt64FromString(tBuf, tmp);
|
||||
result = static_cast<double>(tmp);
|
||||
result = static_cast<ESPEASY_RULES_FLOAT_TYPE>(tmp);
|
||||
return isvalid;
|
||||
}
|
||||
|
||||
@@ -142,7 +142,7 @@ bool validDoubleFromString(const String& tBuf, double& result) {
|
||||
#else // if defined(CORE_POST_2_5_0) || defined(ESP32)
|
||||
float tmp = static_cast<float>(result);
|
||||
bool res = validFloatFromString(tBuf, tmp);
|
||||
result = static_cast<double>(tmp);
|
||||
result = static_cast<ESPEASY_RULES_FLOAT_TYPE>(tmp);
|
||||
return res;
|
||||
#endif // if defined(CORE_POST_2_5_0) || defined(ESP32)
|
||||
}
|
||||
|
||||
@@ -8,7 +8,7 @@
|
||||
\*********************************************************************************************/
|
||||
|
||||
bool isValidFloat(float f);
|
||||
bool isValidDouble(double f);
|
||||
bool isValidDouble(ESPEASY_RULES_FLOAT_TYPE f);
|
||||
|
||||
bool validIntFromString(const String& tBuf, int& result);
|
||||
|
||||
@@ -20,7 +20,7 @@ bool validUInt64FromString(const String& tBuf, uint64_t& result);
|
||||
|
||||
bool validFloatFromString(const String& tBuf, float& result);
|
||||
|
||||
bool validDoubleFromString(const String& tBuf, double& result);
|
||||
bool validDoubleFromString(const String& tBuf, ESPEASY_RULES_FLOAT_TYPE& result);
|
||||
|
||||
// Numerical types sorted from least specific to most specific.
|
||||
enum class NumericalType {
|
||||
|
||||
@@ -72,7 +72,7 @@ bool ruleMatch(String event, String rule) {
|
||||
|
||||
|
||||
// parse event into verb and value
|
||||
double value = 0;
|
||||
ESPEASY_RULES_FLOAT_TYPE value{};
|
||||
int equal_pos = event.indexOf('=');
|
||||
|
||||
if (equal_pos >= 0) {
|
||||
@@ -94,7 +94,7 @@ bool ruleMatch(String event, String rule) {
|
||||
}
|
||||
|
||||
const bool stringMatch = event.equalsIgnoreCase(rule.substring(0, posStart));
|
||||
double ruleValue = 0;
|
||||
ESPEASY_RULES_FLOAT_TYPE ruleValue{};
|
||||
|
||||
if (!validDoubleFromString(rule.substring(posEnd), ruleValue)) {
|
||||
return false;
|
||||
@@ -126,7 +126,7 @@ bool compareIntValues(char compare, const int& Value1, const int& Value2)
|
||||
return false;
|
||||
}
|
||||
|
||||
bool compareDoubleValues(char compare, const double& Value1, const double& Value2)
|
||||
bool compareDoubleValues(char compare, const ESPEASY_RULES_FLOAT_TYPE& Value1, const ESPEASY_RULES_FLOAT_TYPE& Value2)
|
||||
{
|
||||
switch (compare) {
|
||||
case '>' + '=': return !definitelyLessThan(Value1, Value2);
|
||||
|
||||
@@ -16,8 +16,8 @@ bool compareIntValues(char compare,
|
||||
const int& Value2);
|
||||
|
||||
bool compareDoubleValues(char compare,
|
||||
const double& Value1,
|
||||
const double& Value2);
|
||||
const ESPEASY_RULES_FLOAT_TYPE& Value1,
|
||||
const ESPEASY_RULES_FLOAT_TYPE& Value2);
|
||||
|
||||
bool findCompareCondition(const String& check,
|
||||
char & compare,
|
||||
|
||||
@@ -71,7 +71,7 @@ bool RulesCalculate_t::is_unary_operator(char c)
|
||||
*/
|
||||
}
|
||||
|
||||
CalculateReturnCode RulesCalculate_t::push(double value)
|
||||
CalculateReturnCode RulesCalculate_t::push(ESPEASY_RULES_FLOAT_TYPE value)
|
||||
{
|
||||
if (sp != sp_max) // Full
|
||||
{
|
||||
@@ -81,7 +81,7 @@ CalculateReturnCode RulesCalculate_t::push(double value)
|
||||
return CalculateReturnCode::ERROR_STACK_OVERFLOW;
|
||||
}
|
||||
|
||||
double RulesCalculate_t::pop()
|
||||
ESPEASY_RULES_FLOAT_TYPE RulesCalculate_t::pop()
|
||||
{
|
||||
if (sp != (globalstack - 1)) { // empty
|
||||
return *(sp--);
|
||||
@@ -91,7 +91,7 @@ double RulesCalculate_t::pop()
|
||||
}
|
||||
}
|
||||
|
||||
double RulesCalculate_t::apply_operator(char op, double first, double second)
|
||||
ESPEASY_RULES_FLOAT_TYPE RulesCalculate_t::apply_operator(char op, ESPEASY_RULES_FLOAT_TYPE first, ESPEASY_RULES_FLOAT_TYPE second)
|
||||
{
|
||||
switch (op)
|
||||
{
|
||||
@@ -104,36 +104,72 @@ double RulesCalculate_t::apply_operator(char op, double first, double second)
|
||||
case '/':
|
||||
return first / second;
|
||||
case '%':
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
return static_cast<int>(round(first)) % static_cast<int>(round(second));
|
||||
#else
|
||||
return static_cast<int>(roundf(first)) % static_cast<int>(roundf(second));
|
||||
#endif
|
||||
case '^':
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
return pow(first, second);
|
||||
#else
|
||||
return powf(first, second);
|
||||
#endif
|
||||
default:
|
||||
return 0.0;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
double RulesCalculate_t::apply_unary_operator(char op, double first)
|
||||
ESPEASY_RULES_FLOAT_TYPE RulesCalculate_t::apply_unary_operator(char op, ESPEASY_RULES_FLOAT_TYPE first)
|
||||
{
|
||||
double ret = 0.0;
|
||||
ESPEASY_RULES_FLOAT_TYPE ret{};
|
||||
const UnaryOperator un_op = static_cast<UnaryOperator>(op);
|
||||
|
||||
switch (un_op) {
|
||||
case UnaryOperator::Not:
|
||||
return essentiallyZero(roundf(first)) ? 1.0 : 0.0;
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
return essentiallyZero(round(first)) ? 1 : 0;
|
||||
#else
|
||||
return essentiallyZero(roundf(first)) ? 1 : 0;
|
||||
#endif
|
||||
case UnaryOperator::Log:
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
return log10(first);
|
||||
#else
|
||||
return log10f(first);
|
||||
#endif
|
||||
case UnaryOperator::Ln:
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
return log(first);
|
||||
#else
|
||||
return logf(first);
|
||||
#endif
|
||||
case UnaryOperator::Abs:
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
return fabs(first);
|
||||
#else
|
||||
return fabs(first);
|
||||
#endif
|
||||
case UnaryOperator::Exp:
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
return exp(first);
|
||||
#else
|
||||
return expf(first);
|
||||
#endif
|
||||
case UnaryOperator::Sqrt:
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
return sqrt(first);
|
||||
#else
|
||||
return sqrtf(first);
|
||||
#endif
|
||||
case UnaryOperator::Sq:
|
||||
return first * first;
|
||||
case UnaryOperator::Round:
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
return round(first);
|
||||
#else
|
||||
return roundf(first);
|
||||
#endif
|
||||
default:
|
||||
break;
|
||||
}
|
||||
@@ -145,15 +181,27 @@ double RulesCalculate_t::apply_unary_operator(char op, double first)
|
||||
switch (un_op) {
|
||||
case UnaryOperator::ArcSin:
|
||||
case UnaryOperator::ArcSin_d:
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
ret = asin(first);
|
||||
#else
|
||||
ret = asinf(first);
|
||||
#endif
|
||||
return useDegree ? degrees(ret) : ret;
|
||||
case UnaryOperator::ArcCos:
|
||||
case UnaryOperator::ArcCos_d:
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
ret = acos(first);
|
||||
#else
|
||||
ret = acosf(first);
|
||||
#endif
|
||||
return useDegree ? degrees(ret) : ret;
|
||||
case UnaryOperator::ArcTan:
|
||||
case UnaryOperator::ArcTan_d:
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
ret = atan(first);
|
||||
#else
|
||||
ret = atanf(first);
|
||||
#endif
|
||||
return useDegree ? degrees(ret) : ret;
|
||||
default:
|
||||
break;
|
||||
@@ -167,13 +215,25 @@ double RulesCalculate_t::apply_unary_operator(char op, double first)
|
||||
switch (un_op) {
|
||||
case UnaryOperator::Sin:
|
||||
case UnaryOperator::Sin_d:
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
return sin(first);
|
||||
#else
|
||||
return sinf(first);
|
||||
#endif
|
||||
case UnaryOperator::Cos:
|
||||
case UnaryOperator::Cos_d:
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
return cos(first);
|
||||
#else
|
||||
return cosf(first);
|
||||
#endif
|
||||
case UnaryOperator::Tan:
|
||||
case UnaryOperator::Tan_d:
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
return tan(first);
|
||||
#else
|
||||
return tanf(first);
|
||||
#endif
|
||||
default:
|
||||
break;
|
||||
}
|
||||
@@ -220,8 +280,8 @@ CalculateReturnCode RulesCalculate_t::RPNCalculate(char *token)
|
||||
|
||||
if (is_operator(token[0]) && (token[1] == 0))
|
||||
{
|
||||
double second = pop();
|
||||
double first = pop();
|
||||
ESPEASY_RULES_FLOAT_TYPE second = pop();
|
||||
ESPEASY_RULES_FLOAT_TYPE first = pop();
|
||||
|
||||
ret = push(apply_operator(token[0], first, second));
|
||||
|
||||
@@ -229,7 +289,7 @@ CalculateReturnCode RulesCalculate_t::RPNCalculate(char *token)
|
||||
// if (isError(ret)) { return ret; }
|
||||
} else if (is_unary_operator(token[0]) && (token[1] == 0))
|
||||
{
|
||||
double first = pop();
|
||||
ESPEASY_RULES_FLOAT_TYPE first = pop();
|
||||
|
||||
ret = push(apply_unary_operator(token[0], first));
|
||||
|
||||
@@ -237,7 +297,7 @@ CalculateReturnCode RulesCalculate_t::RPNCalculate(char *token)
|
||||
// if (isError(ret)) { return ret; }
|
||||
} else {
|
||||
// Fetch next if there is any
|
||||
double value = 0.0;
|
||||
ESPEASY_RULES_FLOAT_TYPE value{};
|
||||
validDoubleFromString(token, value);
|
||||
|
||||
ret = push(value); // If it is a value, push to the stack
|
||||
@@ -295,7 +355,7 @@ unsigned int RulesCalculate_t::op_arg_count(const char c)
|
||||
return 0;
|
||||
}
|
||||
|
||||
CalculateReturnCode RulesCalculate_t::doCalculate(const char *input, double *result)
|
||||
CalculateReturnCode RulesCalculate_t::doCalculate(const char *input, ESPEASY_RULES_FLOAT_TYPE *result)
|
||||
{
|
||||
|
||||
#ifndef BUILD_NO_RAM_TRACKER
|
||||
|
||||
@@ -60,9 +60,9 @@ const __FlashStringHelper* toString(UnaryOperator op);
|
||||
class RulesCalculate_t {
|
||||
private:
|
||||
|
||||
double globalstack[STACK_SIZE]{};
|
||||
double *sp = globalstack - 1;
|
||||
const double *sp_max = &globalstack[STACK_SIZE - 1];
|
||||
ESPEASY_RULES_FLOAT_TYPE globalstack[STACK_SIZE]{};
|
||||
ESPEASY_RULES_FLOAT_TYPE *sp = globalstack - 1;
|
||||
const ESPEASY_RULES_FLOAT_TYPE *sp_max = &globalstack[STACK_SIZE - 1];
|
||||
|
||||
// Check if it matches part of a number (identifier)
|
||||
// @param oc Previous character
|
||||
@@ -74,16 +74,16 @@ private:
|
||||
|
||||
bool is_unary_operator(char c);
|
||||
|
||||
CalculateReturnCode push(double value);
|
||||
CalculateReturnCode push(ESPEASY_RULES_FLOAT_TYPE value);
|
||||
|
||||
double pop();
|
||||
ESPEASY_RULES_FLOAT_TYPE pop();
|
||||
|
||||
double apply_operator(char op,
|
||||
double first,
|
||||
double second);
|
||||
ESPEASY_RULES_FLOAT_TYPE apply_operator(char op,
|
||||
ESPEASY_RULES_FLOAT_TYPE first,
|
||||
ESPEASY_RULES_FLOAT_TYPE second);
|
||||
|
||||
double apply_unary_operator(char op,
|
||||
double first);
|
||||
ESPEASY_RULES_FLOAT_TYPE apply_unary_operator(char op,
|
||||
ESPEASY_RULES_FLOAT_TYPE first);
|
||||
|
||||
// char * next_token(char *linep);
|
||||
|
||||
@@ -105,7 +105,7 @@ public:
|
||||
RulesCalculate_t();
|
||||
|
||||
CalculateReturnCode doCalculate(const char *input,
|
||||
double *result);
|
||||
ESPEASY_RULES_FLOAT_TYPE *result);
|
||||
|
||||
// Try to replace multi byte operators with single character ones.
|
||||
// For example log, sin, cos, tan.
|
||||
|
||||
@@ -31,7 +31,7 @@ String toString(const float& value, unsigned int decimalPlaces)
|
||||
}
|
||||
}
|
||||
#endif // ifndef LIMIT_BUILD_SIZE
|
||||
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
// This has been fixed in ESP32 code, not (yet) in ESP8266 code
|
||||
// https://github.com/espressif/arduino-esp32/pull/6138/files
|
||||
// #ifdef ESP8266
|
||||
@@ -43,9 +43,9 @@ String toString(const float& value, unsigned int decimalPlaces)
|
||||
String sValue(dtostrf(value, (decimalPlaces + 2), decimalPlaces, buf));
|
||||
free(buf);
|
||||
|
||||
// #else
|
||||
// String sValue = String(value, decimalPlaces);
|
||||
// #endif
|
||||
#else
|
||||
String sValue = String(value, decimalPlaces);
|
||||
#endif
|
||||
|
||||
sValue.trim();
|
||||
return sValue;
|
||||
@@ -89,7 +89,33 @@ String ll2String(int64_t value, uint8_t base) {
|
||||
}
|
||||
}
|
||||
|
||||
String doubleToString(const double& value, unsigned int decimalPlaces, bool trimTrailingZeros) {
|
||||
String trimTrailingZeros(const String& value) {
|
||||
String res(value);
|
||||
int dot_pos = res.lastIndexOf('.');
|
||||
|
||||
if (dot_pos != -1) {
|
||||
bool someTrimmed = false;
|
||||
|
||||
for (int i = res.length() - 1; i > dot_pos && res[i] == '0'; --i) {
|
||||
someTrimmed = true;
|
||||
res[i] = ' ';
|
||||
}
|
||||
|
||||
if (someTrimmed) {
|
||||
res.trim();
|
||||
}
|
||||
|
||||
if (res.endsWith(F("."))) {
|
||||
res[dot_pos] = ' ';
|
||||
res.trim();
|
||||
}
|
||||
}
|
||||
return res;
|
||||
|
||||
}
|
||||
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
String doubleToString(const double& value, unsigned int decimalPlaces, bool trimTrailingZeros_b) {
|
||||
// This has been fixed in ESP32 code, not (yet) in ESP8266 code
|
||||
// https://github.com/espressif/arduino-esp32/pull/6138/files
|
||||
// #ifdef ESP8266
|
||||
@@ -114,29 +140,25 @@ String doubleToString(const double& value, unsigned int decimalPlaces, bool trim
|
||||
// #endif
|
||||
res.trim();
|
||||
|
||||
if (trimTrailingZeros) {
|
||||
int dot_pos = res.lastIndexOf('.');
|
||||
|
||||
if (dot_pos != -1) {
|
||||
bool someTrimmed = false;
|
||||
|
||||
for (int i = res.length() - 1; i > dot_pos && res[i] == '0'; --i) {
|
||||
someTrimmed = true;
|
||||
res[i] = ' ';
|
||||
}
|
||||
|
||||
if (someTrimmed) {
|
||||
res.trim();
|
||||
}
|
||||
|
||||
if (res.endsWith(F("."))) {
|
||||
res[dot_pos] = ' ';
|
||||
res.trim();
|
||||
}
|
||||
}
|
||||
if (trimTrailingZeros_b) {
|
||||
return trimTrailingZeros(res);
|
||||
}
|
||||
return res;
|
||||
}
|
||||
#endif
|
||||
|
||||
String floatToString(const float& value,
|
||||
unsigned int decimalPlaces,
|
||||
bool trimTrailingZeros_b)
|
||||
{
|
||||
const String res = toString(value, decimalPlaces);
|
||||
|
||||
if (trimTrailingZeros_b) {
|
||||
return trimTrailingZeros(res);
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
||||
|
||||
/********************************************************************************************\
|
||||
Check if valid float and convert string to float.
|
||||
|
||||
@@ -28,8 +28,16 @@ String ull2String(uint64_t value,
|
||||
String ll2String(int64_t value,
|
||||
uint8_t base = 10);
|
||||
|
||||
String trimTrailingZeros(const String& value);
|
||||
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
String doubleToString(const double& value,
|
||||
unsigned int decimalPlaces = 2,
|
||||
bool trimTrailingZeros = false);
|
||||
#endif
|
||||
|
||||
String floatToString(const float& value,
|
||||
unsigned int decimalPlaces = 2,
|
||||
bool trimTrailingZeros = false);
|
||||
|
||||
#endif // ifndef HELPERS_STRINGCONVERTER_NUMERICAL_H
|
||||
|
||||
@@ -80,7 +80,7 @@ String parseTemplate_padded(String& tmpString, uint8_t minimal_lineSize, bool us
|
||||
unsigned int varNum;
|
||||
|
||||
if (validUIntFromString(valueName, varNum)) {
|
||||
unsigned char nr_decimals = maxNrDecimals_double(getCustomFloatVar(varNum));
|
||||
unsigned char nr_decimals = maxNrDecimals_fpType(getCustomFloatVar(varNum));
|
||||
bool trimTrailingZeros = true;
|
||||
|
||||
if (devNameEqInt) {
|
||||
@@ -90,7 +90,11 @@ String parseTemplate_padded(String& tmpString, uint8_t minimal_lineSize, bool us
|
||||
// There is some formatting here, so do not throw away decimals
|
||||
trimTrailingZeros = false;
|
||||
}
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
String value = doubleToString(getCustomFloatVar(varNum), nr_decimals, trimTrailingZeros);
|
||||
#else
|
||||
String value = floatToString(getCustomFloatVar(varNum), nr_decimals, trimTrailingZeros);
|
||||
#endif
|
||||
transformValue(
|
||||
newString,
|
||||
minimal_lineSize,
|
||||
@@ -332,7 +336,7 @@ void transformValue(
|
||||
if (valueFormat.length() > 0) // do the checks only if a Format is defined to optimize loop
|
||||
{
|
||||
int logicVal = 0;
|
||||
double valFloat = 0.0;
|
||||
ESPEASY_RULES_FLOAT_TYPE valFloat{};
|
||||
|
||||
if (validDoubleFromString(value, valFloat))
|
||||
{
|
||||
@@ -428,7 +432,11 @@ void transformValue(
|
||||
break;
|
||||
}
|
||||
bool trimTrailingZeros = false;
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
value = doubleToString(valFloat, y, trimTrailingZeros);
|
||||
#else
|
||||
value = floatToString(valFloat, y, trimTrailingZeros);
|
||||
#endif
|
||||
int indexDot = value.indexOf('.');
|
||||
|
||||
if (indexDot == -1) {
|
||||
@@ -441,10 +449,18 @@ void transformValue(
|
||||
break;
|
||||
}
|
||||
case 'F': // FLOOR (round down)
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
value = static_cast<int>(floor(valFloat));
|
||||
#else
|
||||
value = static_cast<int>(floorf(valFloat));
|
||||
#endif
|
||||
break;
|
||||
case 'E': // CEILING (round up)
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
value = static_cast<int>(ceil(valFloat));
|
||||
#else
|
||||
value = static_cast<int>(ceilf(valFloat));
|
||||
#endif
|
||||
break;
|
||||
default:
|
||||
value = F("ERR");
|
||||
|
||||
@@ -274,8 +274,12 @@ void SystemVariables::parseSystemVariables(String& s, boolean useURLencode)
|
||||
key += '%';
|
||||
|
||||
if (s.indexOf(key) != -1) {
|
||||
const bool trimTrailingZeros = true;
|
||||
const String value = doubleToString(getCustomFloatVar(i), 6, trimTrailingZeros);
|
||||
const bool trimTrailingZeros = true;
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
const String value = doubleToString(getCustomFloatVar(i), 6, trimTrailingZeros);
|
||||
#else
|
||||
const String value = floatToString(getCustomFloatVar(i), 6, trimTrailingZeros);
|
||||
#endif
|
||||
repl(key, value, s, useURLencode);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -269,13 +269,28 @@ void P002_data_struct::webformLoad(struct EventStruct *event)
|
||||
addFormTextBox(F("query-input widenumber"),
|
||||
label,
|
||||
getPluginCustomArgName(varNr),
|
||||
_multipoint.size() > line_nr ? doubleToString(static_cast<double>(_multipoint[line_nr]._adc), _nrDecimals,
|
||||
true) : EMPTY_STRING,
|
||||
|
||||
_multipoint.size() > line_nr ?
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
doubleToString
|
||||
#else
|
||||
floatToString
|
||||
#endif
|
||||
(static_cast<ESPEASY_RULES_FLOAT_TYPE>(_multipoint[line_nr]._adc),
|
||||
_nrDecimals,
|
||||
true) : EMPTY_STRING,
|
||||
0);
|
||||
html_add_estimate_symbol();
|
||||
addTextBox(getPluginCustomArgName(varNr + 1),
|
||||
_multipoint.size() > line_nr ? doubleToString(static_cast<double>(_multipoint[line_nr]._value), _nrDecimals,
|
||||
true) : EMPTY_STRING,
|
||||
_multipoint.size() > line_nr ?
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
doubleToString
|
||||
#else
|
||||
floatToString
|
||||
#endif
|
||||
(static_cast<ESPEASY_RULES_FLOAT_TYPE>(_multipoint[line_nr]._value),
|
||||
_nrDecimals,
|
||||
true) : EMPTY_STRING,
|
||||
0,
|
||||
false,
|
||||
false,
|
||||
@@ -950,7 +965,7 @@ int P002_data_struct::computeADC_to_bin(const int& currentValue) const
|
||||
|
||||
formula.replace(F("%value%"), toString(calibrated_value, _nrDecimals));
|
||||
|
||||
double result = 0;
|
||||
ESPEASY_RULES_FLOAT_TYPE result{};
|
||||
|
||||
if (!isError(RulesCalculate.doCalculate(parseTemplate(formula).c_str(), &result))) {
|
||||
calibrated_value = result;
|
||||
|
||||
@@ -173,9 +173,9 @@ bool P008_data_struct::plugin_once_a_second(struct EventStruct *event) {
|
||||
// uint64_t outvalue = castHexAsDec(invalue);
|
||||
// info.reserve(40);
|
||||
// info += F("Test castHexAsDec(");
|
||||
// info += (double)invalue;
|
||||
// info += (ESPEASY_RULES_FLOAT_TYPE)invalue;
|
||||
// info += F(") => ");
|
||||
// info += (double)outvalue;
|
||||
// info += (ESPEASY_RULES_FLOAT_TYPE)outvalue;
|
||||
// addLog(LOG_LEVEL_INFO, info);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -80,39 +80,39 @@ unsigned long P032_data_struct::read_adc(unsigned char aCMD)
|
||||
void P032_data_struct::readout() {
|
||||
unsigned long D1 = 0, D2 = 0;
|
||||
|
||||
double dT;
|
||||
double Offset;
|
||||
double SENS;
|
||||
ESPEASY_RULES_FLOAT_TYPE dT;
|
||||
ESPEASY_RULES_FLOAT_TYPE Offset;
|
||||
ESPEASY_RULES_FLOAT_TYPE SENS;
|
||||
|
||||
D2 = read_adc(MS5xxx_CMD_ADC_D2 + MS5xxx_CMD_ADC_4096);
|
||||
D1 = read_adc(MS5xxx_CMD_ADC_D1 + MS5xxx_CMD_ADC_4096);
|
||||
|
||||
// calculate 1st order pressure and temperature (MS5611 1st order algorithm)
|
||||
dT = D2 - ms5611_prom[5] * static_cast<double>(1 << 8);
|
||||
Offset = ms5611_prom[2] * static_cast<double>(1 << 16) + dT * ms5611_prom[4] / static_cast<double>(1 << 7);
|
||||
SENS = ms5611_prom[1] * static_cast<double>(1 << 15) + dT * ms5611_prom[3] / static_cast<double>(1 << 8);
|
||||
ms5611_temperature = (2000 + (dT * ms5611_prom[6]) / static_cast<double>(1 << 23));
|
||||
dT = D2 - ms5611_prom[5] * static_cast<ESPEASY_RULES_FLOAT_TYPE>(1 << 8);
|
||||
Offset = ms5611_prom[2] * static_cast<ESPEASY_RULES_FLOAT_TYPE>(1 << 16) + dT * ms5611_prom[4] / static_cast<ESPEASY_RULES_FLOAT_TYPE>(1 << 7);
|
||||
SENS = ms5611_prom[1] * static_cast<ESPEASY_RULES_FLOAT_TYPE>(1 << 15) + dT * ms5611_prom[3] / static_cast<ESPEASY_RULES_FLOAT_TYPE>(1 << 8);
|
||||
ms5611_temperature = (2000 + (dT * ms5611_prom[6]) / static_cast<ESPEASY_RULES_FLOAT_TYPE>(1 << 23));
|
||||
|
||||
// perform higher order corrections
|
||||
double T2 = 0., OFF2 = 0., SENS2 = 0.;
|
||||
ESPEASY_RULES_FLOAT_TYPE T2 = 0., OFF2 = 0., SENS2 = 0.;
|
||||
|
||||
if (ms5611_temperature < 2000) {
|
||||
T2 = dT * dT / static_cast<double>(1 << 31);
|
||||
const double temp_20deg = ms5611_temperature - 2000;
|
||||
OFF2 = 5.0 * temp_20deg * temp_20deg / static_cast<double>(1 << 1);
|
||||
SENS2 = 5.0 * temp_20deg * temp_20deg / static_cast<double>(1 << 2);
|
||||
T2 = dT * dT / static_cast<ESPEASY_RULES_FLOAT_TYPE>(1 << 31);
|
||||
const ESPEASY_RULES_FLOAT_TYPE temp_20deg = ms5611_temperature - 2000;
|
||||
OFF2 = 5.0 * temp_20deg * temp_20deg / static_cast<ESPEASY_RULES_FLOAT_TYPE>(1 << 1);
|
||||
SENS2 = 5.0 * temp_20deg * temp_20deg / static_cast<ESPEASY_RULES_FLOAT_TYPE>(1 << 2);
|
||||
|
||||
if (ms5611_temperature < -1500) {
|
||||
const double temp_min15deg = ms5611_temperature + 1500;
|
||||
const ESPEASY_RULES_FLOAT_TYPE temp_min15deg = ms5611_temperature + 1500;
|
||||
OFF2 += 7.0 * temp_min15deg * temp_min15deg;
|
||||
SENS2 += 11.0 * temp_min15deg * temp_min15deg / static_cast<double>(1 << 1);
|
||||
SENS2 += 11.0 * temp_min15deg * temp_min15deg / static_cast<ESPEASY_RULES_FLOAT_TYPE>(1 << 1);
|
||||
}
|
||||
}
|
||||
|
||||
ms5611_temperature -= T2;
|
||||
Offset -= OFF2;
|
||||
SENS -= SENS2;
|
||||
ms5611_pressure = (((D1 * SENS) / static_cast<double>(1 << 21) - Offset) / static_cast<double>(1 << 15));
|
||||
ms5611_pressure = (((D1 * SENS) / static_cast<ESPEASY_RULES_FLOAT_TYPE>(1 << 21) - Offset) / static_cast<ESPEASY_RULES_FLOAT_TYPE>(1 << 15));
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -40,8 +40,8 @@ public:
|
||||
|
||||
uint8_t i2cAddress;
|
||||
unsigned int ms5611_prom[8] = { 0 };
|
||||
double ms5611_pressure = 0;
|
||||
double ms5611_temperature = 0;
|
||||
ESPEASY_RULES_FLOAT_TYPE ms5611_pressure = 0;
|
||||
ESPEASY_RULES_FLOAT_TYPE ms5611_temperature = 0;
|
||||
};
|
||||
#endif // ifdef USES_P032
|
||||
#endif // ifndef PLUGINSTRUCTS_P032_DATA_STRUCT_H
|
||||
|
||||
@@ -665,13 +665,13 @@ String P037_data_struct::mapValue(const String& input, const String& attribute)
|
||||
}
|
||||
case 1: // % => percentage of mapping
|
||||
{
|
||||
double inputDouble;
|
||||
double mappingDouble;
|
||||
ESPEASY_RULES_FLOAT_TYPE inputDouble;
|
||||
ESPEASY_RULES_FLOAT_TYPE mappingDouble;
|
||||
|
||||
if (validDoubleFromString(input, inputDouble) &&
|
||||
validDoubleFromString(valu, mappingDouble)) {
|
||||
if (compareDoubleValues('>', mappingDouble, 0.0)) {
|
||||
double resultDouble = (100.0 / mappingDouble) * inputDouble; // Simple calculation to percentage
|
||||
ESPEASY_RULES_FLOAT_TYPE resultDouble = (static_cast<ESPEASY_RULES_FLOAT_TYPE>(100) / mappingDouble) * inputDouble; // Simple calculation to percentage
|
||||
int8_t decimals = 0;
|
||||
int8_t dotPos = input.indexOf('.');
|
||||
|
||||
@@ -774,7 +774,7 @@ bool P037_data_struct::checkFilters(const String& key, const String& value, int8
|
||||
String filters = P037_FILTER_LIST;
|
||||
String valueData = value;
|
||||
String fltKey, fltIndex, filterData, fltOper;
|
||||
double from, to, doubleValue;
|
||||
ESPEASY_RULES_FLOAT_TYPE from, to, doubleValue;
|
||||
int8_t rangeSeparator;
|
||||
bool accept = true;
|
||||
bool matchTopicId = true;
|
||||
|
||||
@@ -90,7 +90,7 @@ static const uint8_t DefaultCharTable[42] PROGMEM = {
|
||||
// - pos 25 - exclamation mark "!" B01101011
|
||||
// - pos 26 - question mark "?" B01101001
|
||||
// - pos 27 - single quote "'" B00000010
|
||||
// - pos 28 - double quote '"' B00100010
|
||||
// - pos 28 - ESPEASY_RULES_FLOAT_TYPE quote '"' B00100010
|
||||
// - pos 29 - left sharp bracket "<" B01000010
|
||||
// - pos 30 - right sharp bracket ">" B01100000
|
||||
// - pos 31 - backslash "\" B00010011
|
||||
|
||||
@@ -250,7 +250,7 @@ bool P082_data_struct::storeCurPos(unsigned int maxAge_msec) {
|
||||
|
||||
// Return the distance in meters compared to last stored position.
|
||||
// @retval -1 when no fix.
|
||||
double P082_data_struct::distanceSinceLast(unsigned int maxAge_msec) {
|
||||
ESPEASY_RULES_FLOAT_TYPE P082_data_struct::distanceSinceLast(unsigned int maxAge_msec) {
|
||||
if (!hasFix(maxAge_msec)) {
|
||||
return -1.0;
|
||||
}
|
||||
@@ -451,8 +451,8 @@ bool P082_data_struct::webformLoad_show_stats(struct EventStruct *event, uint8_t
|
||||
}
|
||||
|
||||
bool show_custom = false;
|
||||
double dist_p2p = 0.0;
|
||||
double dist_stddev = 0.0;
|
||||
ESPEASY_RULES_FLOAT_TYPE dist_p2p{};
|
||||
ESPEASY_RULES_FLOAT_TYPE dist_stddev{};
|
||||
|
||||
if (gps != nullptr) {
|
||||
switch (query_type) {
|
||||
|
||||
@@ -86,7 +86,7 @@ struct P082_data_struct : public PluginTaskData_base {
|
||||
|
||||
// Return the distance in meters compared to last stored position.
|
||||
// @retval -1 when no fix.
|
||||
double distanceSinceLast(unsigned int maxAge_msec);
|
||||
ESPEASY_RULES_FLOAT_TYPE distanceSinceLast(unsigned int maxAge_msec);
|
||||
|
||||
// Return the GPS time stamp, which is in UTC.
|
||||
// @param age is the time in msec since the last update of the time +
|
||||
@@ -131,11 +131,11 @@ public:
|
||||
TinyGPSPlus *gps = nullptr;
|
||||
ESPeasySerial *easySerial = nullptr;
|
||||
|
||||
double _last_lat = 0.0;
|
||||
double _last_lng = 0.0;
|
||||
double _ref_lat = 0.0;
|
||||
double _ref_lng = 0.0;
|
||||
double _distance = 0.0;
|
||||
ESPEASY_RULES_FLOAT_TYPE _last_lat{};
|
||||
ESPEASY_RULES_FLOAT_TYPE _last_lng{};
|
||||
ESPEASY_RULES_FLOAT_TYPE _ref_lat{};
|
||||
ESPEASY_RULES_FLOAT_TYPE _ref_lng{};
|
||||
ESPEASY_RULES_FLOAT_TYPE _distance{};
|
||||
|
||||
|
||||
unsigned long _pps_time = 0;
|
||||
|
||||
@@ -338,9 +338,9 @@ struct P104_bargraph_struct {
|
||||
P104_bargraph_struct() = delete; // Not used, so leave out explicitly
|
||||
P104_bargraph_struct(uint8_t _graph) : graph(_graph) {}
|
||||
|
||||
double value = 0.0;
|
||||
double max = 0.0;
|
||||
double min = 0.0;
|
||||
ESPEASY_RULES_FLOAT_TYPE value{};
|
||||
ESPEASY_RULES_FLOAT_TYPE max{};
|
||||
ESPEASY_RULES_FLOAT_TYPE min{};
|
||||
uint8_t graph;
|
||||
uint8_t barType = 0u;
|
||||
uint8_t direction = 0u;
|
||||
|
||||
@@ -413,9 +413,11 @@ void addHtmlFloat(const float& value, unsigned int nrDecimals) {
|
||||
addHtml(toString(value, nrDecimals));
|
||||
}
|
||||
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
void addHtmlFloat(const double& value, unsigned int nrDecimals) {
|
||||
addHtml(doubleToString(value, nrDecimals));
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
void addEncodedHtml(const __FlashStringHelper * html) {
|
||||
|
||||
@@ -127,7 +127,9 @@ void addHtmlInt(uint32_t int_val);
|
||||
void addHtmlInt(int64_t int_val);
|
||||
void addHtmlInt(uint64_t int_val);
|
||||
void addHtmlFloat(const float& value, unsigned int nrDecimals = 2u);
|
||||
#if FEATURE_USE_DOUBLE_AS_ESPEASY_RULES_FLOAT_TYPE
|
||||
void addHtmlFloat(const double& value, unsigned int nrDecimals = 2u);
|
||||
#endif
|
||||
|
||||
void addEncodedHtml(const __FlashStringHelper * html);
|
||||
void addEncodedHtml(const String& html);
|
||||
|
||||
Reference in New Issue
Block a user