summaryrefslogtreecommitdiff
path: root/glcdskin/function.c
diff options
context:
space:
mode:
Diffstat (limited to 'glcdskin/function.c')
-rw-r--r--glcdskin/function.c87
1 files changed, 66 insertions, 21 deletions
diff --git a/glcdskin/function.c b/glcdskin/function.c
index 8582ad5..a2d58ca 100644
--- a/glcdskin/function.c
+++ b/glcdskin/function.c
@@ -22,7 +22,7 @@ namespace GLCD
static const char * Internals[] =
{
- "not", "and", "or", "equal", "gt", "lt", "ge", "le", "ne", "file", "trans",
+ "not", "and", "or", "equal", "eq", "gt", "lt", "ge", "le", "ne", "file", "trans",
"add", "sub", "mul", "div",
"FontTotalWidth",
"FontTotalHeight",
@@ -33,6 +33,7 @@ static const char * Internals[] =
"FontTextHeight",
"ImageWidth",
"ImageHeight",
+ "QueryFeature",
NULL
};
@@ -74,7 +75,7 @@ cSkinFunction::~cSkinFunction()
delete mParams[i];
}
-bool cSkinFunction::Parse(const std::string & Text)
+bool cSkinFunction::Parse(const std::string & Text, bool reparse)
{
const char *text = Text.c_str();
const char *ptr = text, *last = text;
@@ -89,7 +90,8 @@ bool cSkinFunction::Parse(const std::string & Text)
|| (*ptr == '\'' && *(ptr + strlen(ptr) - 1) != '\'')
|| (*ptr == '{' && *(ptr + strlen(ptr) - 1) != '}'))
{
- syslog(LOG_ERR, "ERROR: Unmatched string end\n");
+ if (!reparse) // only log this error when not reparsing
+ syslog(LOG_ERR, "ERROR: graphlcd/skin/function: Unmatched string end\n");
return false;
}
@@ -113,7 +115,8 @@ bool cSkinFunction::Parse(const std::string & Text)
// must be a variable id
if (strlen(ptr) < 2)
{
- syslog(LOG_ERR, "ERROR: No variable id given\n");
+ if (!reparse) // only log this error when not reparsing
+ syslog(LOG_ERR, "ERROR: graphlcd/skin/function: No variable id given\n");
return false;
}
@@ -127,7 +130,8 @@ bool cSkinFunction::Parse(const std::string & Text)
int num = strtol(ptr, &end, 10);
if (end == ptr || *end != '\0')
{
- syslog(LOG_ERR, "ERROR: Invalid numeric value\n");
+ // don't log this because when parsing a string starting with a digit (eg: 0%) this may result in a load of false positives
+ //syslog(LOG_ERR, "ERROR: Invalid numeric value (%s)\n", Text.c_str());
return false;
}
@@ -136,9 +140,17 @@ bool cSkinFunction::Parse(const std::string & Text)
}
else
{
+ bool inToken = false;
+
// expression
for (; *ptr; ++ptr)
{
+
+ if (*ptr == '{')
+ inToken = true;
+ else if (inToken && *ptr == '}')
+ inToken = false;
+
if (*ptr == '(')
{
if (inExpr++ == 0)
@@ -156,17 +168,19 @@ bool cSkinFunction::Parse(const std::string & Text)
if (Internals[i] == NULL)
{
- syslog(LOG_ERR, "ERROR: Unknown function %.*s", (int)(ptr - last), last);
+ if (!reparse) // only log this error when not reparsing
+ syslog(LOG_ERR, "ERROR: graphlcd/skin/function: Unknown function %.*s", (int)(ptr - last), last);
return false;
}
last = ptr + 1;
}
}
- else if (*ptr == ',' || *ptr == ')')
+ else if ( ( (!inToken) && (*ptr == ',') ) || *ptr == ')')
{
if (inExpr == 0)
{
- syslog(LOG_ERR, "ERROR: Unmatched '%c' in expression", *ptr);
+ if (!reparse) // only log this error when not reparsing
+ syslog(LOG_ERR, "ERROR: graphlcd/skin/function: Unmatched '%c' in expression (%s)", *ptr, Text.c_str());
return false;
}
@@ -181,8 +195,9 @@ bool cSkinFunction::Parse(const std::string & Text)
if (mNumParams == MAXPARAMETERS)
{
- syslog(LOG_ERR, "ERROR: Too many parameters to function, maximum is %d",
- MAXPARAMETERS);
+ if (!reparse) // only log this error when not reparsing
+ syslog(LOG_ERR, "ERROR: graphlcd/skin/function: Too many parameters to function, maximum is %d",
+ MAXPARAMETERS);
return false;
}
@@ -204,6 +219,7 @@ bool cSkinFunction::Parse(const std::string & Text)
params = -1;
break;
+ case fun_equal:
case fun_eq:
case fun_ne:
case fun_gt:
@@ -247,13 +263,17 @@ bool cSkinFunction::Parse(const std::string & Text)
params = 1;
break;
+ case funQueryFeature:
+ params = 1;
+ break;
+
default:
break;
}
if (params != -1 && mNumParams != (uint32_t) params)
{
- syslog(LOG_ERR, "ERROR: Text2Skin: Wrong number of parameters to %s, "
+ syslog(LOG_ERR, "ERROR: graphlcd/skin/function: Wrong number of parameters to %s, "
"expecting %d", Internals[mType - INTERNAL], params);
return false;
}
@@ -266,7 +286,9 @@ bool cSkinFunction::Parse(const std::string & Text)
if (inExpr > 0)
{
- syslog(LOG_ERR, "ERROR: Expecting ')' in expression");
+ // only log this error when not reparsing
+ if (!reparse)
+ syslog(LOG_ERR, "ERROR: Expecting ')' in expression");
return false;
}
}
@@ -345,8 +367,21 @@ cType cSkinFunction::Evaluate(void) const
case variable:
{
cSkinVariable * variable = mSkin->GetVariable(mVariableId);
- if (variable)
- return variable->Value();
+ if (variable) {
+ cType rv = variable->Value();
+ if (rv.IsString()) {
+ std::string val = rv;
+ if (val.find("{") != std::string::npos || val.find("#") != std::string::npos) {
+ cSkinString *result = new cSkinString(mObject, false);
+ if (result->Parse(val)) {
+ val = (std::string) result->Evaluate();
+ rv = cType(val);
+ }
+ delete result;
+ }
+ }
+ return rv;
+ }
return false;
}
@@ -369,23 +404,24 @@ cType cSkinFunction::Evaluate(void) const
}
return false;
+ case fun_equal:
case fun_eq:
- return mParams[0]->Evaluate() == mParams[1]->Evaluate();
+ return (std::string) mParams[0]->Evaluate() == (std::string) mParams[1]->Evaluate();
case fun_ne:
- return mParams[0]->Evaluate() != mParams[1]->Evaluate();
+ return (std::string) mParams[0]->Evaluate() != (std::string) mParams[1]->Evaluate();
case fun_gt:
- return mParams[0]->Evaluate() > mParams[1]->Evaluate();
+ return (int) mParams[0]->Evaluate() > (int) mParams[1]->Evaluate();
case fun_lt:
- return mParams[0]->Evaluate() < mParams[1]->Evaluate();
+ return (int) mParams[0]->Evaluate() < (int) mParams[1]->Evaluate();
case fun_ge:
- return mParams[0]->Evaluate() >= mParams[1]->Evaluate();
+ return (int) mParams[0]->Evaluate() >= (int) mParams[1]->Evaluate();
case fun_le:
- return mParams[0]->Evaluate() <= mParams[1]->Evaluate();
+ return (int) mParams[0]->Evaluate() <= (int) mParams[1]->Evaluate();
case fun_file:
return FunFile(mParams[0]->Evaluate());
@@ -443,9 +479,18 @@ cType cSkinFunction::Evaluate(void) const
case funImageHeight:
return FunImage(mType, mParams[0]->Evaluate());
+ case funQueryFeature: {
+ int value;
+ if (mSkin->Config().GetDriver()->GetFeature((const std::string)(mParams[0]->Evaluate()), value)) {
+ return (value) ? true : false;
+ } else {
+ return false;
+ }
+ }
+
default:
//Dprintf("unknown function code\n");
- syslog(LOG_ERR, "ERROR: Unknown function code called (this shouldn't happen)");
+ syslog(LOG_ERR, "ERROR: graphlcd/skin/function: Unknown function code called (this shouldn't happen)");
break;
}
return false;