vdr-plugin-skindesigner/libtemplate/templateloopfunction.c
2015-03-31 05:34:41 +02:00

233 lines
7.3 KiB
C

#include "templateloopfunction.h"
#include "../libcore/helpers.h"
using namespace std;
// --- cTemplateFunction -------------------------------------------------------------
cTemplateLoopFunction::cTemplateLoopFunction(void) : cTemplateFunction(ftLoop) {
}
cTemplateLoopFunction::~cTemplateLoopFunction(void) {
}
void cTemplateLoopFunction::InitIterator(void) {
funcIt = functions.begin();
}
void cTemplateLoopFunction::AddFunction(string name, vector<pair<string, string> > &params) {
eFuncType type = ftNone;
if (!name.compare("drawtext")) {
type = ftDrawText;
} else if (!name.compare("drawtextbox")) {
type = ftDrawTextBox;
} else if (!name.compare("drawimage")) {
type = ftDrawImage;
} else if (!name.compare("drawrectangle")) {
type = ftDrawRectangle;
} else if (!name.compare("drawellipse")) {
type = ftDrawEllipse;
}
if (type == ftNone) {
return;
}
cTemplateFunction *f = new cTemplateFunction(type);
f->SetParameters(params);
functions.push_back(f);
}
void cTemplateLoopFunction::CalculateLoopFuncParameters(void) {
int columnWidth = GetNumericParameter(ptColumnWidth);
int rowHeight = GetNumericParameter(ptRowHeight);
for (vector<cTemplateFunction*>::iterator func = functions.begin(); func != functions.end(); func++) {
(*func)->SetGlobals(globals);
(*func)->SetContainer(0, 0, containerWidth, containerHeight);
(*func)->SetLoopContainer(columnWidth, rowHeight);
(*func)->CalculateParameters();
(*func)->CompleteParameters();
}
}
cTemplateFunction *cTemplateLoopFunction::GetNextFunction(void) {
if (funcIt == functions.end())
return NULL;
cTemplateFunction *func = *funcIt;
funcIt++;
return func;
}
void cTemplateLoopFunction::ClearDynamicParameters(void) {
InitIterator();
cTemplateFunction *func = NULL;
while(func = GetNextFunction()) {
func->ClearDynamicParameters();
}
}
void cTemplateLoopFunction::ParseDynamicParameters(map <string,string> *tokens) {
if (!tokens)
return;
InitIterator();
cTemplateFunction *func = NULL;
map <string,int> intTokens;
for (map <string,string>::iterator it = tokens->begin(); it != tokens->end(); it++) {
if (isNumber(it->second))
intTokens.insert(pair<string, int>(it->first, atoi((it->second).c_str())));
}
bool completelyParsed = true;
while(func = GetNextFunction()) {
func->SetStringTokens(tokens);
func->SetIntTokens(&intTokens);
bool funcCompletelyParsed = func->ParseParameters();
if (!funcCompletelyParsed)
completelyParsed = false;
if (func->Updated())
func->CompleteParameters();
func->UnsetStringTokens();
func->UnsetIntTokens();
}
if (completelyParsed) {
return;
}
bool replacedWidth = ReplaceWidthFunctions();
bool replacedHeight = ReplaceHeightFunctions();
if (!replacedWidth && !replacedHeight)
return;
InitIterator();
func = NULL;
while(func = GetNextFunction()) {
if (func->ParsedCompletely())
continue;
func->SetStringTokens(tokens);
func->SetIntTokens(&intTokens);
func->ParseParameters();
if (func->Updated())
func->CompleteParameters();
func->UnsetIntTokens();
func->UnsetStringTokens();
}
}
int cTemplateLoopFunction::GetLoopElementsWidth(void) {
int cW = GetNumericParameter(ptColumnWidth);
if (cW > 0) {
return cW;
}
InitIterator();
cTemplateFunction *func = NULL;
int maxWidth = 1;
while(func = GetNextFunction()) {
int funcWidth = func->GetWidth(true);
if (funcWidth > maxWidth)
maxWidth = funcWidth;
}
return maxWidth;
}
int cTemplateLoopFunction::GetLoopElementsHeight(void) {
int rH = GetNumericParameter(ptRowHeight);
if (rH > 0)
return rH;
InitIterator();
cTemplateFunction *func = NULL;
int maxHeight = 1;
while(func = GetNextFunction()) {
int funcY = func->GetNumericParameter(ptY);
int funcHeight = func->GetHeight();
int totalHeight = funcY + funcHeight;
if (totalHeight > maxHeight)
maxHeight = totalHeight;
}
return maxHeight;
}
bool cTemplateLoopFunction::ReplaceWidthFunctions(void) {
bool replaced = false;
InitIterator();
cTemplateFunction *func = NULL;
while(func = GetNextFunction()) {
if (func->ParsedCompletely()) {
continue;
}
multimap<eParamType,string> widths;
func->GetNeededWidths(&widths);
for (map<eParamType, string>::iterator names = widths.begin(); names !=widths.end(); names++) {
eParamType type = names->first;
string label = names->second;
int funcWidth = 0;
for (vector<cTemplateFunction*>::iterator it = functions.begin(); it != functions.end(); it++) {
cTemplateFunction *myFunc = *it;
string myFuncName = myFunc->GetParameter(ptName);
if (!myFuncName.compare(label)) {
funcWidth = myFunc->GetWidth();
func->SetWidth(type, label, funcWidth);
if (func->Updated()) {
func->CompleteParameters();
} else {
replaced = true;
}
}
}
}
}
return replaced;
}
bool cTemplateLoopFunction::ReplaceHeightFunctions(void) {
bool replaced = false;
InitIterator();
cTemplateFunction *func = NULL;
while(func = GetNextFunction()) {
if (func->ParsedCompletely()) {
continue;
}
multimap<eParamType,string> heights;
func->GetNeededHeights(&heights);
for (map<eParamType, string>::iterator names = heights.begin(); names !=heights.end(); names++) {
eParamType type = names->first;
string label = names->second;
int funcHeight = 0;
for (vector<cTemplateFunction*>::iterator it = functions.begin(); it != functions.end(); it++) {
cTemplateFunction *myFunc = *it;
string myFuncName = myFunc->GetParameter(ptName);
if (!myFuncName.compare(label)) {
funcHeight = myFunc->GetHeight();
func->SetHeight(type, label, funcHeight);
if (func->Updated()) {
func->CompleteParameters();
} else {
replaced = true;
}
}
}
}
}
return replaced;
}
bool cTemplateLoopFunction::Ready(void) {
bool isReady = true;
map< eParamType, string >::iterator hit = numericDynamicParameters.find(ptColumnWidth);
if (hit != numericDynamicParameters.end())
isReady = false;
hit = numericDynamicParameters.find(ptRowHeight);
if (hit != numericDynamicParameters.end())
isReady = false;
return isReady;
}
void cTemplateLoopFunction::Debug(void) {
cTemplateFunction::Debug();
esyslog("skindesigner: functions to be looped:");
for (vector<cTemplateFunction*>::iterator func = functions.begin(); func != functions.end(); func++) {
(*func)->Debug();
}
}