/*************************************************************************** kommanderfunctions.cpp - Text widget core functionality ------------------- copyright : (C) 2004 Michal Rudolf ***************************************************************************/ /*************************************************************************** * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 2 of the License, or * * (at your option) any later version. * * * ***************************************************************************/ #include #include #include #include #include #include #include #include #include #include #include "kommanderwidget.h" #include "specials.h" #include "specialinformation.h" #include "expression.h" #include "parser.h" TQString KommanderWidget::evalFunction(const TQString& function, const TQStringList& args) { switch (SpecialInformation::function(Group::Kommander, function)) { case Kommander::widgetText: return handleDCOP(DCOP::text); case Kommander::selectedWidgetText: return handleDCOP(DCOP::selection); case Kommander::dcopid: return kapp->dcopClient()->appId(); case Kommander::pid: return TQString().setNum(getpid()); case Kommander::null: return TQString(); case Kommander::comment: return TQString("#"); case Kommander::exec: return execCommand(args[0]); case Kommander::dcop: return DCOPQuery(args); case Kommander::parentPid: return global("_PARENTPID").isEmpty() ? TQString().setNum(getppid()) : global("_PARENTPID"); case Kommander::env: return TQString(getenv(args[0].latin1())); case Kommander::i18n: return TDEGlobal::locale()->translate(args[0].utf8()); case Kommander::global: return global(args[0]); case Kommander::setGlobal: setGlobal(args[0], args[1]); return TQString(); case Kommander::debug: tqDebug("%s", args[0].latin1()); fflush(stderr); return TQString(); case Kommander::echo: for (uint i=0; i 1) return runDialog(args[0], args[1]); else return runDialog(args[0]); case Kommander::expr: { Expression expr(args[0]); bool ok; TQVariant value = expr.value(&ok); return ok ? value.toString() : TQString(); } default: return TQString(); } } TQString KommanderWidget::evalExecBlock(const TQStringList& args, const TQString& s, int& pos) { int f = s.find("@execEnd", pos); if (f == -1) { printError(i18n("Unterminated @execBegin ... @execEnd block.")); return TQString(); } else { TQString shell = args.count() ? args[0] : TQString(); int start = pos; pos = f + TQString("@execEnd").length()+1; return execCommand(evalAssociatedText(s.mid(start, f - start)), shell); } } TQString KommanderWidget::evalForEachBlock(const TQStringList& args, const TQString& s, int& pos) { int f = s.find("@end", pos); //FIXME: better detection of block boundaries if (f == -1) { printError(i18n("Unterminated @forEach ... @end block.")); return TQString(); } else { int start = pos; pos = f + TQString("@end").length()+1; TQString var = args[0]; TQStringList loop = TQStringList::split("\n", args[1]); TQString output; TQString block = substituteVariable(s.mid(start, f - start), TQString("%1_count").arg(var), TQString::number(loop.count())); TQString varidx = TQString("%1_index").arg(var); for (uint i=0; i 3) { loopstep = expr.value(args[3]).toInt(); if (!loopstep) loopstep = 1; } TQString output; for (int i=loopstart; i<=loopend; i+=loopstep) { output += evalAssociatedText(substituteVariable(block, variable, TQString::number(i))); } return output; } } TQString KommanderWidget::evalIfBlock(const TQStringList& args, const TQString& s, int& pos) { int f = s.find("@endif", pos); //FIXME: better detection of block boundaries; add error message if (f == -1) { pos = s.length()+1; printError(i18n("Unterminated @if ... @endif block.")); return TQString(); } else { TQString block = s.mid(pos, f - pos); pos = f + TQString("@endif").length()+1; Expression expr; if (expr.isTrue(args[0])) return evalAssociatedText(block); return TQString(); } } TQString KommanderWidget::evalSwitchBlock(const TQStringList& args, const TQString& s, int& pos) { int f = s.find("@end", pos); //FIXME: better detection of block boundaries; add error message if (f == -1) { printError(i18n("Unterminated @switch ... @end block.")); return TQString(); } else { TQString block = s.mid(pos, f - pos); pos = f + TQString("@end").length()+1; f = parseBlockBoundary(block, 0, "@case"); bool finished = f == -1; while (!finished) { f += 5; int end = parseBlockBoundary(block, f, "@case"); if (end == -1) { end = block.length(); finished = true; } bool ok; TQString value = parseBrackets(block, f, ok); if (!ok) break; if (value == args[0] || value == "*") return evalAssociatedText(block.mid(f, end-f)); f = end; } return TQString(); } } TQString KommanderWidget::evalArrayFunction(const TQString& function, const TQStringList& args) { Parser parser(internalParserData()); int fname = SpecialInformation::function(Group::Array, function); TQString array = args[0].startsWith("_") ? args[0] : TQString("_")+ args[0]; if (fname == Array::setValue) parser.setArray(array, args[1], args[2]); else if (fname == Array::fromString) { TQStringList lines = TQStringList::split("\n", args[1]); for (TQStringList::Iterator it = lines.begin(); it != lines.end(); ++it) { TQString key = (*it).section('\t', 0, 0).stripWhiteSpace(); if (!key.isEmpty()) parser.setArray(array, key, (*it).section('\t', 1)); } } else if (!parser.isArray(array)) return TQString(); else switch (fname) { case Array::value: return parser.arrayValue(array, args[1]).toString(); case Array::keys: { const TQMap map = parser.array(array); TQStringList keys; for (TQMap::ConstIterator it = map.begin(); it != map.end(); ++it) keys.append(it.key()); return keys.join("\n"); } case Array::values: { const TQMap map = parser.array(array); TQStringList values; for (TQMap::ConstIterator it = map.begin(); it != map.end(); ++it) values.append(it.data().toString()); return values.join("\n"); } case Array::clear: parser.unsetArray(array); return TQString(); case Array::remove: parser.unsetArray(array, args[1]); return TQString(); case Array::count: return TQString::number(parser.array(array).count()); case Array::toString: { const TQMap map = parser.array(array); TQString arraystring; for (TQMap::ConstIterator it = map.begin(); it != map.end(); ++it) arraystring += TQString("%1\t%2\n").arg(it.key()).arg(it.data().toString()); return arraystring; } default: return TQString(); } return TQString(); } TQString KommanderWidget::evalWidgetFunction(const TQString& identifier, const TQString& s, int& pos) { KommanderWidget* pWidget = parseWidget(identifier); if (!pWidget) { printError(i18n("Unknown widget: @%1.").arg(identifier)); return TQString(); } if (s[pos] == '.') { pos++; bool ok = true; TQString function = parseIdentifier(s, pos); TQStringList args = parseFunction("DCOP", function, s, pos, ok); if (!ok) return TQString(); args.prepend(pWidget->widgetName()); TQString prototype = SpecialInformation::prototype(Group::DCOP, SpecialInformation::function(Group::DCOP, function)); return localDCOPQuery(prototype, args); } else if (pWidget == this) { printError(i18n("Infinite loop: @%1 called inside @%2.").arg(pWidget->widgetName()) .arg(pWidget->widgetName())); return TQString(); } else if (!pWidget->hasAssociatedText()) { printError(i18n("Script for @%1 is empty.").arg(pWidget->widgetName())); return TQString(); } return pWidget->evalAssociatedText(); }