Merge pull request #2464 from MichaelDvP/dev

bitmask for bool custom entities as hex value
This commit is contained in:
Proddy
2025-03-13 08:40:33 +01:00
committed by GitHub
16 changed files with 176 additions and 43 deletions

View File

@@ -41,7 +41,7 @@
"typescript": "^5.8.2" "typescript": "^5.8.2"
}, },
"devDependencies": { "devDependencies": {
"@babel/core": "^7.26.9", "@babel/core": "^7.26.10",
"@eslint/js": "^9.22.0", "@eslint/js": "^9.22.0",
"@preact/compat": "^18.3.1", "@preact/compat": "^18.3.1",
"@preact/preset-vite": "^2.10.1", "@preact/preset-vite": "^2.10.1",

View File

@@ -61,7 +61,8 @@ const CustomEntitiesDialog = ({
setEditItem({ setEditItem({
...selectedItem, ...selectedItem,
device_id: selectedItem.device_id.toString(16).toUpperCase(), device_id: selectedItem.device_id.toString(16).toUpperCase(),
type_id: selectedItem.type_id.toString(16).toUpperCase() type_id: selectedItem.type_id.toString(16).toUpperCase(),
factor: selectedItem.value_type === DeviceValueType.BOOL ? selectedItem.factor.toString(16).toUpperCase() : selectedItem.factor
}); });
} }
}, [open, selectedItem]); }, [open, selectedItem]);
@@ -82,6 +83,9 @@ const CustomEntitiesDialog = ({
if (typeof editItem.type_id === 'string') { if (typeof editItem.type_id === 'string') {
editItem.type_id = parseInt(editItem.type_id, 16); editItem.type_id = parseInt(editItem.type_id, 16);
} }
if (editItem.value_type === DeviceValueType.BOOL && typeof editItem.factor === 'string') {
editItem.factor = parseInt(editItem.factor, 16);
}
onSave(editItem); onSave(editItem);
} catch (error) { } catch (error) {
setFieldErrors(error as ValidateFieldsError); setFieldErrors(error as ValidateFieldsError);
@@ -315,7 +319,7 @@ const CustomEntitiesDialog = ({
<ValidatedTextField <ValidatedTextField
fieldErrors={fieldErrors} fieldErrors={fieldErrors}
name="factor" name="factor"
label="Bytes" label={LL.BYTES()}
value={numberValue(editItem.factor as number)} value={numberValue(editItem.factor as number)}
sx={{ width: '11ch' }} sx={{ width: '11ch' }}
variant="outlined" variant="outlined"
@@ -333,7 +337,7 @@ const CustomEntitiesDialog = ({
<ValidatedTextField <ValidatedTextField
fieldErrors={fieldErrors} fieldErrors={fieldErrors}
name="factor" name="factor"
label="Mask" label={LL.BITMASK()}
value={editItem.factor as string} value={editItem.factor as string}
sx={{ width: '11ch' }} sx={{ width: '11ch' }}
variant="outlined" variant="outlined"

View File

@@ -340,6 +340,8 @@ const cz: Translation = {
AUTO_SCROLL: 'Automatické rolování', AUTO_SCROLL: 'Automatické rolování',
DASHBOARD: 'Dashboard', DASHBOARD: 'Dashboard',
DEVELOPER_MODE: 'Režim vývojáře', DEVELOPER_MODE: 'Režim vývojáře',
BYTES: 'Bytes', // TODO translate
BITMASK: 'Bit Mask',// TODO translate
DUPLICATE: 'Duplikát', DUPLICATE: 'Duplikát',
UPGRADE: 'Upgrade', UPGRADE: 'Upgrade',
DASHBOARD_1: 'Všechny aktivní entity EMS jsou označené jako oblíbené. Všechny vlastní entity, harmonogramy a externí sensory jsou zobrazeny níže.', DASHBOARD_1: 'Všechny aktivní entity EMS jsou označené jako oblíbené. Všechny vlastní entity, harmonogramy a externí sensory jsou zobrazeny níže.',

View File

@@ -340,6 +340,8 @@ const de: Translation = {
AUTO_SCROLL: 'Automatisches Scrollen', AUTO_SCROLL: 'Automatisches Scrollen',
DASHBOARD: 'Dashboard', DASHBOARD: 'Dashboard',
DEVELOPER_MODE: 'Entwicklermodus', DEVELOPER_MODE: 'Entwicklermodus',
BYTES: 'Bytes',
BITMASK: 'Bit Maske',
DUPLICATE: 'Kopieren', DUPLICATE: 'Kopieren',
UPGRADE: 'Aktualisieren', UPGRADE: 'Aktualisieren',
DASHBOARD_1: 'Alle EMS-Entitäten, die aktiv und als Favorit markiert sind, sowie alle benutzerdefinierten Entitäten, Zeitpläne und externen Sensordaten werden unten angezeigt.', DASHBOARD_1: 'Alle EMS-Entitäten, die aktiv und als Favorit markiert sind, sowie alle benutzerdefinierten Entitäten, Zeitpläne und externen Sensordaten werden unten angezeigt.',

View File

@@ -341,6 +341,8 @@ const en: Translation = {
DASHBOARD: 'Dashboard', DASHBOARD: 'Dashboard',
DASHBOARD_1: 'All EMS entities that are active and marked as Favorite, plus all Custom Entities, Schedules and external Sensors data are displayed below.', DASHBOARD_1: 'All EMS entities that are active and marked as Favorite, plus all Custom Entities, Schedules and external Sensors data are displayed below.',
DEVELOPER_MODE: 'Developer Mode', DEVELOPER_MODE: 'Developer Mode',
BYTES: 'Bytes',
BITMASK: 'Bit Mask',
DUPLICATE: 'Duplicate', DUPLICATE: 'Duplicate',
UPGRADE: 'Upgrade', UPGRADE: 'Upgrade',
NO_DATA_1: 'No favorite EMS entities found yet. Use the', NO_DATA_1: 'No favorite EMS entities found yet. Use the',

View File

@@ -340,6 +340,8 @@ const fr: Translation = {
AUTO_SCROLL: 'Auto Scroll', // TODO translate AUTO_SCROLL: 'Auto Scroll', // TODO translate
DASHBOARD: 'Dashboard', // TODO translate DASHBOARD: 'Dashboard', // TODO translate
DEVELOPER_MODE: 'Developer Mode', // TODO translate DEVELOPER_MODE: 'Developer Mode', // TODO translate
BYTES: 'Bytes', // TODO translate
BITMASK: 'Bit Mask',// TODO translate
DUPLICATE: 'Duplicate', // TODO translate DUPLICATE: 'Duplicate', // TODO translate
UPGRADE: 'Upgrade', // TODO translate UPGRADE: 'Upgrade', // TODO translate
DASHBOARD_1: 'All EMS entities that are active and marked as Favorite, plus all Custom Entities, Schedules and external Sensors data are displayed below.', // TODO translate DASHBOARD_1: 'All EMS entities that are active and marked as Favorite, plus all Custom Entities, Schedules and external Sensors data are displayed below.', // TODO translate

View File

@@ -340,6 +340,8 @@ const it: Translation = {
AUTO_SCROLL: 'Auto Scroll', // TODO translate AUTO_SCROLL: 'Auto Scroll', // TODO translate
DASHBOARD: 'Dashboard', // TODO translate DASHBOARD: 'Dashboard', // TODO translate
DEVELOPER_MODE: 'Developer Mode', // TODO translate DEVELOPER_MODE: 'Developer Mode', // TODO translate
BYTES: 'Bytes', // TODO translate
BITMASK: 'Bit Mask',// TODO translate
DUPLICATE: 'Duplicate', // TODO translate DUPLICATE: 'Duplicate', // TODO translate
UPGRADE: 'Upgrade', // TODO translate UPGRADE: 'Upgrade', // TODO translate
DASHBOARD_1: 'All EMS entities that are active and marked as Favorite, plus all Custom Entities, Schedules and external Sensors data are displayed below.', // TODO translate DASHBOARD_1: 'All EMS entities that are active and marked as Favorite, plus all Custom Entities, Schedules and external Sensors data are displayed below.', // TODO translate

View File

@@ -340,6 +340,8 @@ const nl: Translation = {
AUTO_SCROLL: 'Automatisch Scrollen', AUTO_SCROLL: 'Automatisch Scrollen',
DASHBOARD: 'Dashboard', DASHBOARD: 'Dashboard',
DEVELOPER_MODE: 'Ontwikkelaarsmodus', DEVELOPER_MODE: 'Ontwikkelaarsmodus',
BYTES: 'Bytes', // TODO translate
BITMASK: 'Bit Mask',// TODO translate
DUPLICATE: 'Duplicaat', DUPLICATE: 'Duplicaat',
UPGRADE: 'Upgraden', UPGRADE: 'Upgraden',
DASHBOARD_1: 'Alle EMS-entiteiten die actief zijn en als favoriet zijn gemarkeerd, plus alle aangepaste entiteiten en externe sensorgegevens worden hieronder weergegeven.', DASHBOARD_1: 'Alle EMS-entiteiten die actief zijn en als favoriet zijn gemarkeerd, plus alle aangepaste entiteiten en externe sensorgegevens worden hieronder weergegeven.',

View File

@@ -340,6 +340,8 @@ const no: Translation = {
AUTO_SCROLL: 'Auto Scroll', // TODO translate AUTO_SCROLL: 'Auto Scroll', // TODO translate
DASHBOARD: 'Dashboard', // TODO translate DASHBOARD: 'Dashboard', // TODO translate
DEVELOPER_MODE: 'Developer Mode', // TODO translate DEVELOPER_MODE: 'Developer Mode', // TODO translate
BYTES: 'Bytes', // TODO translate
BITMASK: 'Bit Mask',// TODO translate
DUPLICATE: 'Duplicate', // TODO translate DUPLICATE: 'Duplicate', // TODO translate
UPGRADE: 'Upgrade', // TODO translate UPGRADE: 'Upgrade', // TODO translate
DASHBOARD_1: 'All EMS entities that are active and marked as Favorite, plus all Custom Entities, Schedules and external Sensors data are displayed below.', // TODO translate DASHBOARD_1: 'All EMS entities that are active and marked as Favorite, plus all Custom Entities, Schedules and external Sensors data are displayed below.', // TODO translate

View File

@@ -340,6 +340,8 @@ const pl: BaseTranslation = {
AUTO_SCROLL: 'Auto Scroll', // TODO translate AUTO_SCROLL: 'Auto Scroll', // TODO translate
DASHBOARD: 'Dashboard', // TODO translate DASHBOARD: 'Dashboard', // TODO translate
DEVELOPER_MODE: 'Developer Mode', // TODO translate DEVELOPER_MODE: 'Developer Mode', // TODO translate
BYTES: 'Bytes', // TODO translate
BITMASK: 'Bit Mask',// TODO translate
DUPLICATE: 'Duplicate', // TODO translate DUPLICATE: 'Duplicate', // TODO translate
UPGRADE: 'Upgrade', // TODO translate UPGRADE: 'Upgrade', // TODO translate
DASHBOARD_1: 'All EMS entities that are active and marked as Favorite, plus all Custom Entities, Schedules and external Sensors data are displayed below.', // TODO translate DASHBOARD_1: 'All EMS entities that are active and marked as Favorite, plus all Custom Entities, Schedules and external Sensors data are displayed below.', // TODO translate

View File

@@ -340,6 +340,8 @@ const sk: Translation = {
AUTO_SCROLL: 'Automatické rolovanie', AUTO_SCROLL: 'Automatické rolovanie',
DASHBOARD: 'Panel', DASHBOARD: 'Panel',
DEVELOPER_MODE: 'Režim vývojára', DEVELOPER_MODE: 'Režim vývojára',
BYTES: 'Bytes', // TODO translate
BITMASK: 'Bit Mask',// TODO translate
DUPLICATE: 'Duplicitné', DUPLICATE: 'Duplicitné',
UPGRADE: 'Inovovať', UPGRADE: 'Inovovať',
DASHBOARD_1: 'Všetky entity EMS, ktoré sú aktívne a označené ako obľúbené, plus všetky vlastné entity, plány a údaje externých senzorov sú zobrazené nižšie.', DASHBOARD_1: 'Všetky entity EMS, ktoré sú aktívne a označené ako obľúbené, plus všetky vlastné entity, plány a údaje externých senzorov sú zobrazené nižšie.',

View File

@@ -340,6 +340,8 @@ const sv: Translation = {
AUTO_SCROLL: 'Autoskrolla', AUTO_SCROLL: 'Autoskrolla',
DASHBOARD: 'Kontrollpanel', DASHBOARD: 'Kontrollpanel',
DEVELOPER_MODE: 'Utvecklarläge', DEVELOPER_MODE: 'Utvecklarläge',
BYTES: 'Bytes', // TODO translate
BITMASK: 'Bit Mask',// TODO translate
DUPLICATE: 'Dublett', DUPLICATE: 'Dublett',
UPGRADE: 'Uppgradera', UPGRADE: 'Uppgradera',
DASHBOARD_1: 'All EMS entities that are active and marked as Favorite, plus all Custom Entities, Schedules and external Sensors data are displayed below.', // TODO translate DASHBOARD_1: 'All EMS entities that are active and marked as Favorite, plus all Custom Entities, Schedules and external Sensors data are displayed below.', // TODO translate

View File

@@ -340,6 +340,8 @@ const tr: Translation = {
AUTO_SCROLL: 'Auto Scroll', // TODO translate AUTO_SCROLL: 'Auto Scroll', // TODO translate
DASHBOARD: 'Dashboard', // TODO translate DASHBOARD: 'Dashboard', // TODO translate
DEVELOPER_MODE: 'Developer Mode', // TODO translate DEVELOPER_MODE: 'Developer Mode', // TODO translate
BYTES: 'Bytes', // TODO translate
BITMASK: 'Bit Mask',// TODO translate
DUPLICATE: 'Duplicate', // TODO translate DUPLICATE: 'Duplicate', // TODO translate
UPGRADE: 'Upgrade', // TODO translate UPGRADE: 'Upgrade', // TODO translate
DASHBOARD_1: 'All EMS entities that are active and marked as Favorite, plus all Custom Entities, Schedules and external Sensors data are displayed below.', // TODO translate DASHBOARD_1: 'All EMS entities that are active and marked as Favorite, plus all Custom Entities, Schedules and external Sensors data are displayed below.', // TODO translate

View File

@@ -51,7 +51,7 @@ __metadata:
languageName: node languageName: node
linkType: hard linkType: hard
"@babel/core@npm:^7.22.1, @babel/core@npm:^7.26.9": "@babel/core@npm:^7.22.1":
version: 7.26.9 version: 7.26.9
resolution: "@babel/core@npm:7.26.9" resolution: "@babel/core@npm:7.26.9"
dependencies: dependencies:
@@ -74,6 +74,42 @@ __metadata:
languageName: node languageName: node
linkType: hard linkType: hard
"@babel/core@npm:^7.26.10":
version: 7.26.10
resolution: "@babel/core@npm:7.26.10"
dependencies:
"@ampproject/remapping": "npm:^2.2.0"
"@babel/code-frame": "npm:^7.26.2"
"@babel/generator": "npm:^7.26.10"
"@babel/helper-compilation-targets": "npm:^7.26.5"
"@babel/helper-module-transforms": "npm:^7.26.0"
"@babel/helpers": "npm:^7.26.10"
"@babel/parser": "npm:^7.26.10"
"@babel/template": "npm:^7.26.9"
"@babel/traverse": "npm:^7.26.10"
"@babel/types": "npm:^7.26.10"
convert-source-map: "npm:^2.0.0"
debug: "npm:^4.1.0"
gensync: "npm:^1.0.0-beta.2"
json5: "npm:^2.2.3"
semver: "npm:^6.3.1"
checksum: 10c0/e046e0e988ab53841b512ee9d263ca409f6c46e2a999fe53024688b92db394346fa3aeae5ea0866331f62133982eee05a675d22922a4603c3f603aa09a581d62
languageName: node
linkType: hard
"@babel/generator@npm:^7.26.10":
version: 7.26.10
resolution: "@babel/generator@npm:7.26.10"
dependencies:
"@babel/parser": "npm:^7.26.10"
"@babel/types": "npm:^7.26.10"
"@jridgewell/gen-mapping": "npm:^0.3.5"
"@jridgewell/trace-mapping": "npm:^0.3.25"
jsesc: "npm:^3.0.2"
checksum: 10c0/88b3b3ea80592fc89349c4e1a145e1386e4042866d2507298adf452bf972f68d13bf699a845e6ab8c028bd52c2247013eb1221b86e1db5c9779faacba9c4b10e
languageName: node
linkType: hard
"@babel/generator@npm:^7.26.5, @babel/generator@npm:^7.26.9": "@babel/generator@npm:^7.26.5, @babel/generator@npm:^7.26.9":
version: 7.26.9 version: 7.26.9
resolution: "@babel/generator@npm:7.26.9" resolution: "@babel/generator@npm:7.26.9"
@@ -160,6 +196,16 @@ __metadata:
languageName: node languageName: node
linkType: hard linkType: hard
"@babel/helpers@npm:^7.26.10":
version: 7.26.10
resolution: "@babel/helpers@npm:7.26.10"
dependencies:
"@babel/template": "npm:^7.26.9"
"@babel/types": "npm:^7.26.10"
checksum: 10c0/f99e1836bcffce96db43158518bb4a24cf266820021f6461092a776cba2dc01d9fc8b1b90979d7643c5c2ab7facc438149064463a52dd528b21c6ab32509784f
languageName: node
linkType: hard
"@babel/helpers@npm:^7.26.9": "@babel/helpers@npm:^7.26.9":
version: 7.26.9 version: 7.26.9
resolution: "@babel/helpers@npm:7.26.9" resolution: "@babel/helpers@npm:7.26.9"
@@ -170,6 +216,17 @@ __metadata:
languageName: node languageName: node
linkType: hard linkType: hard
"@babel/parser@npm:^7.26.10":
version: 7.26.10
resolution: "@babel/parser@npm:7.26.10"
dependencies:
"@babel/types": "npm:^7.26.10"
bin:
parser: ./bin/babel-parser.js
checksum: 10c0/c47f5c0f63cd12a663e9dc94a635f9efbb5059d98086a92286d7764357c66bceba18ccbe79333e01e9be3bfb8caba34b3aaebfd8e62c3d5921c8cf907267be75
languageName: node
linkType: hard
"@babel/parser@npm:^7.26.7, @babel/parser@npm:^7.26.9": "@babel/parser@npm:^7.26.7, @babel/parser@npm:^7.26.9":
version: 7.26.9 version: 7.26.9
resolution: "@babel/parser@npm:7.26.9" resolution: "@babel/parser@npm:7.26.9"
@@ -253,6 +310,21 @@ __metadata:
languageName: node languageName: node
linkType: hard linkType: hard
"@babel/traverse@npm:^7.26.10":
version: 7.26.10
resolution: "@babel/traverse@npm:7.26.10"
dependencies:
"@babel/code-frame": "npm:^7.26.2"
"@babel/generator": "npm:^7.26.10"
"@babel/parser": "npm:^7.26.10"
"@babel/template": "npm:^7.26.9"
"@babel/types": "npm:^7.26.10"
debug: "npm:^4.3.1"
globals: "npm:^11.1.0"
checksum: 10c0/4e86bb4e3c30a6162bb91df86329df79d96566c3e2d9ccba04f108c30473a3a4fd360d9990531493d90f6a12004f10f616bf9b9229ca30c816b708615e9de2ac
languageName: node
linkType: hard
"@babel/types@npm:^7.25.9, @babel/types@npm:^7.26.7, @babel/types@npm:^7.26.9": "@babel/types@npm:^7.25.9, @babel/types@npm:^7.26.7, @babel/types@npm:^7.26.9":
version: 7.26.9 version: 7.26.9
resolution: "@babel/types@npm:7.26.9" resolution: "@babel/types@npm:7.26.9"
@@ -263,6 +335,16 @@ __metadata:
languageName: node languageName: node
linkType: hard linkType: hard
"@babel/types@npm:^7.26.10":
version: 7.26.10
resolution: "@babel/types@npm:7.26.10"
dependencies:
"@babel/helper-string-parser": "npm:^7.25.9"
"@babel/helper-validator-identifier": "npm:^7.25.9"
checksum: 10c0/7a7f83f568bfc3dfabfaf9ae3a97ab5c061726c0afa7dcd94226d4f84a81559da368ed79671e3a8039d16f12476cf110381a377ebdea07587925f69628200dac
languageName: node
linkType: hard
"@emotion/babel-plugin@npm:^11.13.5": "@emotion/babel-plugin@npm:^11.13.5":
version: 11.13.5 version: 11.13.5
resolution: "@emotion/babel-plugin@npm:11.13.5" resolution: "@emotion/babel-plugin@npm:11.13.5"
@@ -1591,7 +1673,7 @@ __metadata:
resolution: "EMS-ESP@workspace:." resolution: "EMS-ESP@workspace:."
dependencies: dependencies:
"@alova/adapter-xhr": "npm:2.1.1" "@alova/adapter-xhr": "npm:2.1.1"
"@babel/core": "npm:^7.26.9" "@babel/core": "npm:^7.26.10"
"@emotion/react": "npm:^11.14.0" "@emotion/react": "npm:^11.14.0"
"@emotion/styled": "npm:^11.14.0" "@emotion/styled": "npm:^11.14.0"
"@eslint/js": "npm:^9.22.0" "@eslint/js": "npm:^9.22.0"

View File

@@ -81,9 +81,12 @@ std::deque<Token> exprToTokens(const std::string & expr) {
} else if (strncmp(p, "abs", 3) == 0) { } else if (strncmp(p, "abs", 3) == 0) {
p += 2; p += 2;
tokens.emplace_back(Token::Type::Unary, "a", 5); tokens.emplace_back(Token::Type::Unary, "a", 5);
} else if (strncmp(p, "ln", 2) == 0) {
p += 1;
tokens.emplace_back(Token::Type::Unary, "l", 5);
} else if (strncmp(p, "log", 3) == 0) { } else if (strncmp(p, "log", 3) == 0) {
p += 2; p += 2;
tokens.emplace_back(Token::Type::Unary, "l", 5); tokens.emplace_back(Token::Type::Unary, "g", 5);
} else if (strncmp(p, "exp", 3) == 0) { } else if (strncmp(p, "exp", 3) == 0) {
p += 2; p += 2;
tokens.emplace_back(Token::Type::Unary, "e", 5); tokens.emplace_back(Token::Type::Unary, "e", 5);
@@ -93,6 +96,9 @@ std::deque<Token> exprToTokens(const std::string & expr) {
} else if (strncmp(p, "pow", 3) == 0) { } else if (strncmp(p, "pow", 3) == 0) {
p += 2; p += 2;
tokens.emplace_back(Token::Type::Unary, "p", 5); tokens.emplace_back(Token::Type::Unary, "p", 5);
} else if (strncmp(p, "tohex", 5) == 0) {
p += 4;
tokens.emplace_back(Token::Type::Unary, "x", 5);
} else if (strncmp(p, "hex", 3) == 0) { } else if (strncmp(p, "hex", 3) == 0) {
p += 2; p += 2;
tokens.emplace_back(Token::Type::Unary, "h", 5); tokens.emplace_back(Token::Type::Unary, "h", 5);
@@ -102,7 +108,7 @@ std::deque<Token> exprToTokens(const std::string & expr) {
++p; ++p;
} }
const auto s = std::string(b, p); const auto s = std::string(b, p);
tokens.emplace_back(Token::Type::String, s, -2); tokens.emplace_back(Token::Type::String, s, -3);
--p; --p;
} else if (*p == '"') { } else if (*p == '"') {
++p; ++p;
@@ -132,7 +138,7 @@ std::deque<Token> exprToTokens(const std::string & expr) {
++p; ++p;
} }
const auto s = std::string(b, p); const auto s = std::string(b, p);
tokens.emplace_back(Token::Type::Number, s, -4); tokens.emplace_back(Token::Type::Number, s, -2);
--p; --p;
} else { } else {
Token::Type token = Token::Type::Operator; Token::Type token = Token::Type::Operator;
@@ -203,7 +209,7 @@ std::deque<Token> exprToTokens(const std::string & expr) {
precedence = 1; precedence = 1;
token = Token::Type::Compare; token = Token::Type::Compare;
} else { } else {
precedence = 1; precedence = 2;
token = Token::Type::Unary; token = Token::Type::Unary;
} }
break; break;
@@ -359,9 +365,6 @@ std::string commands(std::string & expr, bool quotes = true) {
if (e == std::string::npos) { if (e == std::string::npos) {
e = expr.length(); e = expr.length();
} }
while (e > 0 && expr[e - 1] == ' ') { // remove blanks from end
e--;
}
char cmd[COMMAND_MAX_LENGTH]; char cmd[COMMAND_MAX_LENGTH];
size_t l = e - f; size_t l = e - f;
if (l >= sizeof(cmd) - 1) { if (l >= sizeof(cmd) - 1) {
@@ -420,6 +423,14 @@ std::string to_string(double d) {
return s; return s;
} }
// number to hex string
std::string to_hex(uint32_t i) {
char c[10];
snprintf(c, 10, "%02X", i);
std::string s = c;
return s;
}
// RPN calculator // RPN calculator
std::string calculate(const std::string & expr) { std::string calculate(const std::string & expr) {
std::string expr_new = expr; std::string expr_new = expr;
@@ -459,46 +470,57 @@ std::string calculate(const std::string & expr) {
} }
const auto rhs = stack.back(); const auto rhs = stack.back();
stack.pop_back(); stack.pop_back();
if (token.str[0] == '!') {
if (to_logic(rhs) < 0) {
}
if (to_logic(rhs) >= 0) {
stack.push_back(to_logic(rhs) == 0 ? "1" : "0");
} else if (isnum(rhs)) {
stack.push_back(std::stod(rhs) == 0 ? "1" : "0");
} else {
emsesp::EMSESP::logger().warning("missing operator");
return "";
}
break;
}
auto rhd = std::stod(rhs);
switch (token.str[0]) { switch (token.str[0]) {
default: default:
return ""; return "";
break; break;
case 'm': // Special operator name for unary '-' case 'm': // Special operator name for unary '-'
if (!isnum(rhs)) { stack.push_back(to_string(-1 * rhd));
return "";
}
stack.push_back(to_string(-1 * std::stod(rhs)));
break;
case '!':
if (to_logic(rhs) < 0) {
return "";
}
stack.push_back(to_logic(rhs) == 0 ? "1" : "0");
break; break;
case 'i': case 'i':
stack.push_back(to_string(std::stoi(rhs))); stack.push_back(to_string(static_cast<int>(rhd)));
break; break;
case 'r': case 'r':
stack.push_back(to_string(std::round(std::stod(rhs)))); stack.push_back(to_string(std::round(rhd)));
break; break;
case 'a': case 'a':
stack.push_back(to_string(std::abs(std::stod(rhs)))); stack.push_back(to_string(std::abs(rhd)));
break; break;
case 'e': case 'e':
stack.push_back(to_string(std::exp(std::stod(rhs)))); stack.push_back(to_string(std::exp(rhd)));
break; break;
case 'l': case 'l':
stack.push_back(to_string(std::log(std::stod(rhs)))); stack.push_back(to_string(std::log(rhd)));
break;
case 'g':
stack.push_back(to_string(std::log10(rhd)));
break; break;
case 's': case 's':
stack.push_back(to_string(std::sqrt(std::stod(rhs)))); stack.push_back(to_string(std::sqrt(rhd)));
break; break;
case 'p': case 'p':
stack.push_back(to_string(std::pow(std::stod(rhs), 2))); stack.push_back(to_string(std::pow(rhd, 2)));
break; break;
case 'h': case 'h':
stack.push_back(to_string(std::stoi(rhs, 0, 16))); stack.push_back(to_string(std::stoi(rhs, 0, 16)));
break; break;
case 'x':
stack.push_back(to_hex(static_cast<int>(rhd)));
break;
} }
} break; } break;
case Token::Type::Compare: { case Token::Type::Compare: {
@@ -585,38 +607,40 @@ std::string calculate(const std::string & expr) {
} break; } break;
case Token::Type::Operator: { case Token::Type::Operator: {
// binary operators // binary operators
if (stack.empty() || !isnum(stack.back())) { if (stack.size() < 2) {
return ""; return "";
} }
const auto rhs = std::stod(stack.back()); const auto rhs = stack.back();
stack.pop_back(); stack.pop_back();
if (stack.empty() || !isnum(stack.back())) { const auto lhs = stack.back();
return ""; stack.pop_back();
if (token.str[0] == '+' && (!isnum(rhs) || !isnum(lhs))) {
stack.push_back(lhs + rhs);
break;
} }
const auto lhs = std::stod(stack.back()); auto lhd = std::stod(lhs);
stack.pop_back(); auto rhd = std::stod(rhs);
switch (token.str[0]) { switch (token.str[0]) {
default: default:
return ""; return "";
break; break;
case '^': case '^':
stack.push_back(to_string(pow(lhs, rhs))); stack.push_back(to_string(pow(lhd, rhd)));
break; break;
case '*': case '*':
stack.push_back(to_string(lhs * rhs)); stack.push_back(to_string(lhd * rhd));
break; break;
case '/': case '/':
stack.push_back(to_string(lhs / rhs)); stack.push_back(to_string(lhd / rhd));
break; break;
case '%': case '%':
stack.push_back(std::to_string(static_cast<int>(lhs) % static_cast<int>(rhs))); stack.push_back(std::to_string(static_cast<int>(lhd) % static_cast<int>(rhd)));
break; break;
case '+': case '+':
stack.push_back(to_string(lhs + rhs)); stack.push_back(to_string(lhd + rhd));
break; break;
case '-': case '-':
stack.push_back(to_string(lhs - rhs)); stack.push_back(to_string(lhd - rhd));
break; break;
} }
} break; } break;

View File

@@ -105,6 +105,7 @@ StateUpdateResult WebCustomEntity::update(JsonObject root, WebCustomEntity & web
if (entityItem.ram == 0 && entityItem.value_type == DeviceValueType::STRING) { if (entityItem.ram == 0 && entityItem.value_type == DeviceValueType::STRING) {
entityItem.raw = new uint8_t[(size_t)entityItem.factor + 1]; entityItem.raw = new uint8_t[(size_t)entityItem.factor + 1];
entityItem.data = ""; entityItem.data = "";
entityItem.uom = 0;
} else if (entityItem.value_type == DeviceValueType::BOOL) { } else if (entityItem.value_type == DeviceValueType::BOOL) {
entityItem.value = EMS_VALUE_DEFAULT_BOOL; entityItem.value = EMS_VALUE_DEFAULT_BOOL;
entityItem.uom = 0; entityItem.uom = 0;