28#undef QT_NO_CAST_FROM_ASCII
30#include <QtCore/QCoreApplication>
31#include <QtCore/QFile>
32#include <QtCore/QFileInfo>
33#include <QtCore/QSettings>
34#include <QtCore/QTextStream>
35#include <QtXml/QDomAttr>
36#include <QtCore/QRegExp>
37#include <QtCore/QStringList>
45 QTextStream cout(stdout);
46 QTextStream cerr(stderr);
52 directory = QChar::fromLatin1(
'.');
54 for (
int i = 1; i < args.count(); ++i) {
55 if (args.at(i) == QLatin1String(
"-d") || args.at(i) == QLatin1String(
"--directory")) {
56 if (i + 1 > args.count()) {
57 cerr << args.at(i) <<
" needs an argument" << endl;
60 directory = args.at(++i);
61 }
else if (args.at(i).startsWith(QLatin1String(
"-d"))) {
62 directory = args.at(i).mid(2);
63 }
else if (args.at(i) == QLatin1String(
"--help") || args.at(i) == QLatin1String(
"-h")) {
64 cout <<
"Options:" << endl;
65 cout <<
" -L --license Display software license" << endl;
66 cout <<
" -d, --directory <dir> Directory to generate files in [.]" << endl;
67 cout <<
" -h, --help Display this help" << endl;
69 cout <<
"Arguments:" << endl;
70 cout <<
" file.kcfg Input kcfg XML file" << endl;
71 cout <<
" file.kcfgc Code generation options file" << endl;
73 }
else if (args.at(i) == QLatin1String(
"--license") || args.at(i) == QLatin1String(
"-L")) {
74 cout <<
"Copyright 2003 Cornelius Schumacher, Waldo Bastian, Zack Rusin," << endl;
75 cout <<
" Reinhold Kainhofer, Duncan Mac-Vicar P., Harald Fernengel" << endl;
76 cout <<
"This program comes with ABSOLUTELY NO WARRANTY." << endl;
77 cout <<
"You may redistribute copies of this program" << endl;
78 cout <<
"under the terms of the GNU Library Public License." << endl;
79 cout <<
"For more information about these matters, see the file named COPYING." << endl;
81 }
else if (args.at(i).startsWith(QLatin1Char(
'-'))) {
82 cerr <<
"Unknown option: " << args.at(i) << endl;
84 }
else if (fileCount == 0) {
87 }
else if (fileCount == 1) {
91 cerr <<
"Too many arguments" << endl;
96 cerr <<
"Too few arguments" << endl;
112 CfgConfig(
const QString &codegenFilename )
115 QSettings codegenConfig(codegenFilename, QSettings::IniFormat);
117 nameSpace = codegenConfig.value(
"NameSpace").toString();
118 className = codegenConfig.value(
"ClassName").toString();
119 if ( className.isEmpty() ) {
120 cerr <<
"Class name missing" << endl;
123 inherits = codegenConfig.value(
"Inherits").toString();
124 if ( inherits.isEmpty() ) inherits =
"KConfigSkeleton";
125 visibility = codegenConfig.value(
"Visibility").toString();
126 if ( !visibility.isEmpty() ) visibility +=
' ';
127 forceStringFilename = codegenConfig.value(
"ForceStringFilename",
false).toBool();
128 singleton = codegenConfig.value(
"Singleton",
false).toBool();
129 staticAccessors = singleton;
130 customAddons = codegenConfig.value(
"CustomAdditions",
false).toBool();
131 memberVariables = codegenConfig.value(
"MemberVariables").toString();
132 dpointer = (memberVariables ==
"dpointer");
133 headerIncludes = codegenConfig.value(
"IncludeFiles",
QStringList()).toStringList();
134 sourceIncludes = codegenConfig.value(
"SourceIncludeFiles",
QStringList()).toStringList();
135 mutators = codegenConfig.value(
"Mutators",
QStringList()).toStringList();
136 allMutators = ((mutators.count() == 1) && (mutators.at(0).toLower() ==
"true"));
137 itemAccessors = codegenConfig.value(
"ItemAccessors",
false).toBool();
138 setUserTexts = codegenConfig.value(
"SetUserTexts",
false).toBool();
139 defaultGetters = codegenConfig.value(
"DefaultValueGetters",
QStringList()).toStringList();
140 allDefaultGetters = (defaultGetters.count() == 1) && (defaultGetters.at(0).toLower() ==
"true");
141 globalEnums = codegenConfig.value(
"GlobalEnums",
false).toBool();
142 useEnumTypes = codegenConfig.value(
"UseEnumTypes",
false).toBool();
151 bool forceStringFilename;
153 bool staticAccessors;
162 bool allDefaultGetters;
170struct SignalArguments
202 :
prefix(p), choices(d), mName(n)
204 int i = n.indexOf(QLatin1String(
"::"));
206 mExternalQual = n.left(i + 2);
210 const QString& name()
const {
return mName; }
211 const QString& externalQualifier()
const {
return mExternalQual; }
212 bool external()
const {
return !mExternalQual.isEmpty(); }
223 : mGroup(
group ), mType( type ), mKey( key ), mName( name ),
224 mLabelContext( labelContext ), mLabel( label ), mToolTipContext( toolTipContext ), mToolTip( toolTip ),
225 mWhatsThisContext( whatsThisContext ), mWhatsThis( whatsThis ),
226 mCode( code ), mDefaultValue(
defaultValue ), mChoices( choices ),
227 mSignalList(signalList), mHidden( hidden )
231 void setGroup(
const QString &group ) { mGroup =
group; }
234 void setType(
const QString &type ) { mType = type; }
235 QString type()
const {
return mType; }
237 void setKey(
const QString &key ) { mKey = key; }
238 QString key()
const {
return mKey; }
240 void setName(
const QString &name ) { mName = name; }
241 QString name()
const {
return mName; }
243 void setLabelContext(
const QString &labelContext ) { mLabelContext = labelContext; }
244 QString labelContext()
const {
return mLabelContext; }
246 void setLabel(
const QString &label ) { mLabel = label; }
247 QString label()
const {
return mLabel; }
249 void setToolTipContext(
const QString &toolTipContext ) { mToolTipContext = toolTipContext; }
250 QString toolTipContext()
const {
return mToolTipContext; }
252 void setToolTip(
const QString &toolTip ) { mToolTip = toolTip; }
253 QString toolTip()
const {
return mToolTip; }
255 void setWhatsThisContext(
const QString &whatsThisContext ) { mWhatsThisContext = whatsThisContext; }
256 QString whatsThisContext()
const {
return mWhatsThisContext; }
258 void setWhatsThis(
const QString &whatsThis ) { mWhatsThis = whatsThis; }
259 QString whatsThis()
const {
return mWhatsThis; }
261 void setDefaultValue(
const QString &d ) { mDefaultValue = d; }
264 void setCode(
const QString &d ) { mCode = d; }
265 QString code()
const {
return mCode; }
267 void setMinValue(
const QString &d ) { mMin = d; }
268 QString minValue()
const {
return mMin; }
270 void setMaxValue(
const QString &d ) { mMax = d; }
271 QString maxValue()
const {
return mMax; }
273 void setParam(
const QString &d ) { mParam = d; }
276 void setParamName(
const QString &d ) { mParamName = d; }
277 QString paramName()
const {
return mParamName; }
279 void setParamType(
const QString &d ) { mParamType = d; }
280 QString paramType()
const {
return mParamType; }
283 Choices choices()
const {
return mChoices; }
285 void setParamValues(
const QStringList &d ) { mParamValues = d; }
286 QStringList paramValues()
const {
return mParamValues; }
288 void setParamDefaultValues(
const QStringList &d ) { mParamDefaultValues = d; }
289 QString paramDefaultValue(
int i)
const {
return mParamDefaultValues[i]; }
291 void setParamMax(
int d ) { mParamMax = d; }
292 int paramMax()
const {
return mParamMax; }
294 void setSignalList(
const QList<Signal> &value ) { mSignalList = value; }
297 bool hidden()
const {
return mHidden; }
301 cerr <<
"<entry>" << endl;
302 cerr <<
" group: " << mGroup << endl;
303 cerr <<
" type: " << mType << endl;
304 cerr <<
" key: " << mKey << endl;
305 cerr <<
" name: " << mName << endl;
306 cerr <<
" label context: " << mLabelContext << endl;
307 cerr <<
" label: " << mLabel << endl;
309 cerr <<
" code: " << mCode << endl;
312 if (!
param().isEmpty())
314 cerr <<
" param name: "<< mParamName << endl;
315 cerr <<
" param type: "<< mParamType << endl;
316 cerr <<
" paramvalues: " << mParamValues.join(QChar::fromLatin1(
':')) << endl;
318 cerr <<
" default: " << mDefaultValue << endl;
319 cerr <<
" hidden: " << mHidden << endl;
320 cerr <<
" min: " << mMin << endl;
321 cerr <<
" max: " << mMax << endl;
322 cerr <<
"</entry>" << endl;
363 if ( !cfg.dpointer ) {
364 result = QChar::fromLatin1(
'm') + n;
365 result[1] = result[1].toUpper();
369 result[0] = result[0].toLower();
377 if ( cfg.dpointer ) {
378 result =
"d->"+
varName(n, cfg);
388 QString result = QString::fromLatin1(
"Enum") + n;
389 result[4] = result[4].toUpper();
396 if ( result.isEmpty() )
398 result = QString::fromLatin1(
"Enum") + n;
399 result[4] = result[4].toUpper();
406 QString result = e->choices().name();
407 if ( result.isEmpty() )
409 result = QString::fromLatin1(
"Enum") + e->name();
411 result += QString::fromLatin1(
"::type");
412 result[4] = result[4].toUpper();
420 if ( result.isEmpty() )
422 result = QString::fromLatin1(
"Enum") + n + QString::fromLatin1(
"::");
423 result[4] = result[4].toUpper();
425 else if ( c.external() )
426 result = c.externalQualifier();
434 QString result = QString::fromLatin1(
"set") + n;
435 result[3] = result[3].toUpper();
437 if ( !className.isEmpty() )
438 result = className + QString::fromLatin1(
"::") + result;
444 QString result = QString::fromLatin1(
"default") + n + QString::fromLatin1(
"Value");
445 result[7] = result[7].toUpper();
447 if ( !className.isEmpty() )
448 result = className + QString::fromLatin1(
"::") + result;
455 result[0] = result[0].toLower();
457 if ( !className.isEmpty() )
458 result = className + QString::fromLatin1(
"::") + result;
465 if ( !s.startsWith( QLatin1Char(
'"') ) )
466 s.prepend( QLatin1Char(
'"') );
467 if ( !s.endsWith( QLatin1Char(
'"') ) )
468 s.append( QLatin1Char(
'"') );
474 r.replace( QLatin1Char(
'\\'), QLatin1String(
"\\\\") );
475 r.replace( QLatin1Char(
'\"'), QLatin1String(
"\\\"") );
476 r.remove( QLatin1Char(
'\r') );
477 r.replace( QLatin1Char(
'\n'), QLatin1String(
"\\n\"\n\"") );
478 return QLatin1Char(
'\"') + r + QLatin1Char(
'\"');
484 for(
int i = s.length(); i--;)
485 if (s[i].unicode() > 127) isAscii =
false;
488 return QString::fromLatin1(
"QLatin1String( ") +
quoteString(s) + QString::fromLatin1(
" )");
490 return QString::fromLatin1(
"QString::fromUtf8( ") +
quoteString(s) + QString::fromLatin1(
" )");
496 QTextStream s(&msg, QIODevice::WriteOnly );
499 msg = msg.simplified();
500 if (msg.length() > 40)
501 return msg.left(37) + QString::fromLatin1(
"...");
507 int i = path.lastIndexOf(QRegExp(QLatin1String(
"[/\\]")));
509 return path.mid(i+1);
516 result = QString::fromLatin1(
"signal") + signalName;
517 result[6] = result[6].toUpper();
524 const CfgEntry::Choices &choices,
525 QString &code,
const CfgConfig &cfg )
527 if ( type == QLatin1String(
"String") && !
defaultValue.isEmpty() ) {
530 }
else if ( type == QLatin1String(
"Path") && !
defaultValue.isEmpty() ) {
532 }
else if ( type == QLatin1String(
"Url") && !
defaultValue.isEmpty() ) {
534 }
else if ( ( type == QLatin1String(
"UrlList") || type == QLatin1String(
"StringList") || type == QLatin1String(
"PathList")) && !
defaultValue.isEmpty() ) {
535 QTextStream cpp( &code, QIODevice::WriteOnly | QIODevice::Append );
539 if( type ==
"UrlList" ) {
540 cpp <<
" KUrl::List default" << name <<
";" << endl;
542 cpp <<
" QStringList default" << name <<
";" << endl;
545 QStringList::ConstIterator it;
546 for( it = defaults.constBegin(); it != defaults.constEnd(); ++it ) {
547 cpp <<
" default" << name <<
".append( ";
548 if( type ==
"UrlList" ) {
551 cpp <<
"QString::fromUtf8( \"" << *it <<
"\" ) ";
552 if( type == QLatin1String(
"UrlList") ) {
559 }
else if ( type == QLatin1String(
"Color") && !
defaultValue.isEmpty() ) {
560 QRegExp colorRe(QLatin1String(
"\\d+,\\s*\\d+,\\s*\\d+(,\\s*\\d+)?"));
570 }
else if ( type == QLatin1String(
"Enum") ) {
572 for( it = choices.choices.constBegin(); it != choices.choices.constEnd(); ++it ) {
574 if ( cfg.globalEnums && choices.name().isEmpty() )
582 }
else if ( type == QLatin1String(
"IntList") ) {
583 QTextStream cpp( &code, QIODevice::WriteOnly | QIODevice::Append );
587 cpp <<
" QList<int> default" << name <<
";" << endl;
591 QStringList::ConstIterator it;
592 for( it = defaults.constBegin(); it != defaults.constEnd(); ++it ) {
593 cpp <<
" default" << name <<
".append( " << *it <<
" );"
604 bool defaultCode =
false;
605 QString type = element.attribute(
"type" );
606 QString name = element.attribute(
"name" );
607 QString key = element.attribute(
"key" );
608 QString hidden = element.attribute(
"hidden" );
620 CfgEntry::Choices choices;
628 for ( QDomElement e = element.firstChildElement(); !e.isNull(); e = e.nextSiblingElement() ) {
630 if ( tag ==
"label" ) {
632 labelContext = e.attribute(
"context" );
634 else if ( tag ==
"tooltip" ) {
636 toolTipContext = e.attribute(
"context" );
638 else if ( tag ==
"whatsthis" ) {
639 whatsThis = e.text();
640 whatsThisContext = e.attribute(
"context" );
642 else if ( tag ==
"min" ) minValue = e.text();
643 else if ( tag ==
"max" ) maxValue = e.text();
644 else if ( tag ==
"code" ) code = e.text();
645 else if ( tag ==
"parameter" )
647 param = e.attribute(
"name" );
648 paramType = e.attribute(
"type" );
649 if (
param.isEmpty() ) {
650 cerr <<
"Parameter must have a name: " <<
dumpNode(e) << endl;
653 if ( paramType.isEmpty() ) {
654 cerr <<
"Parameter must have a type: " <<
dumpNode(e) << endl;
657 if ((paramType ==
"Int") || (paramType ==
"UInt"))
660 paramMax = e.attribute(
"max").toInt(&ok);
663 cerr <<
"Integer parameter must have a maximum (e.g. max=\"0\"): "
668 else if (paramType ==
"Enum")
670 for ( QDomElement e2 = e.firstChildElement(); !e2.isNull(); e2 = e2.nextSiblingElement() ) {
671 if (e2.tagName() ==
"values")
673 for ( QDomElement e3 = e2.firstChildElement(); !e3.isNull(); e3 = e3.nextSiblingElement() ) {
674 if (e3.tagName() ==
"value")
676 paramValues.append( e3.text() );
682 if (paramValues.isEmpty())
684 cerr <<
"No values specified for parameter '" <<
param
688 paramMax = paramValues.count()-1;
692 cerr <<
"Parameter '" <<
param <<
"' has type " << paramType
693 <<
" but must be of type int, uint or Enum." << endl;
697 else if ( tag ==
"default" )
699 if (e.attribute(
"param").isEmpty())
702 if (e.attribute(
"code" ) ==
"true")
706 else if ( tag ==
"choices" ) {
707 QString name = e.attribute(
"name" );
710 for( QDomElement e2 = e.firstChildElement(); !e2.isNull(); e2 = e2.nextSiblingElement() ) {
711 if ( e2.tagName() ==
"choice" ) {
712 CfgEntry::Choice choice;
713 choice.name = e2.attribute(
"name" );
714 if ( choice.name.isEmpty() ) {
715 cerr <<
"Tag <choice> requires attribute 'name'." << endl;
717 for( QDomElement e3 = e2.firstChildElement(); !e3.isNull(); e3 = e3.nextSiblingElement() ) {
718 if ( e3.tagName() ==
"label" ) {
719 choice.label = e3.text();
720 choice.context = e3.attribute(
"context" );
722 if ( e3.tagName() ==
"tooltip" ) {
723 choice.toolTip = e3.text();
724 choice.context = e3.attribute(
"context" );
726 if ( e3.tagName() ==
"whatsthis" ) {
727 choice.whatsThis = e3.text();
728 choice.context = e3.attribute(
"context" );
731 chlist.append( choice );
734 choices = CfgEntry::Choices( chlist, name,
prefix );
736 else if ( tag ==
"emit" ) {
739 signal.name = e.attribute(
"signal" );
740 signalList.append( signal);
745 bool nameIsEmpty = name.isEmpty();
746 if ( nameIsEmpty && key.isEmpty() ) {
747 cerr <<
"Entry must have a name or a key: " <<
dumpNode(element) << endl;
751 if ( key.isEmpty() ) {
758 }
else if ( name.contains(
' ' ) ) {
759 cout<<
"Entry '"<<name<<
"' contains spaces! <name> elements can not contain spaces!"<<endl;
763 if (name.contains(
"$("))
767 cerr <<
"Name may not be parameterized: " << name << endl;
773 if (!
param.isEmpty())
775 cerr <<
"Name must contain '$(" <<
param <<
")': " << name << endl;
780 if ( label.isEmpty() ) {
784 if ( type.isEmpty() ) type =
"String";
786 if (!
param.isEmpty())
790 name.remove(
"$("+
param+
')');
792 for(
int i = 0; i <= paramMax; i++)
794 paramDefaultValues.append(
QString());
797 for ( QDomElement e = element.firstChildElement(); !e.isNull(); e = e.nextSiblingElement() ) {
799 if ( tag ==
"default" )
801 QString index = e.attribute(
"param");
806 int i = index.toInt(&ok);
809 i = paramValues.indexOf(index);
812 cerr <<
"Index '" << index <<
"' for default value is unknown." << endl;
817 if ((i < 0) || (i > paramMax))
819 cerr <<
"Index '" << i <<
"' for default value is out of range [0, "<< paramMax<<
"]." << endl;
823 QString tmpDefaultValue = e.text();
825 if (e.attribute(
"code" ) !=
"true")
828 paramDefaultValues[i] = tmpDefaultValue;
836 cerr <<
"The key '" << key <<
"' can not be used as name for the entry because "
837 "it is not a valid name. You need to specify a valid name for this entry." << endl;
839 cerr <<
"The name '" << name <<
"' is not a valid name for an entry." << endl;
846 cerr <<
"The key '" << key <<
"' can not be used as name for the entry because "
847 "it does not result in a unique name. You need to specify a unique name for this entry." << endl;
849 cerr <<
"The name '" << name <<
"' is not unique." << endl;
859 CfgEntry *result =
new CfgEntry( group, type, key, name, labelContext, label, toolTipContext, toolTip, whatsThisContext, whatsThis,
862 if (!
param.isEmpty())
864 result->setParam(
param);
865 result->setParamName(paramName);
866 result->setParamType(paramType);
867 result->setParamValues(paramValues);
868 result->setParamDefaultValues(paramDefaultValues);
869 result->setParamMax(paramMax);
871 result->setMinValue(minValue);
872 result->setMaxValue(maxValue);
879 if ( type ==
"UInt" )
return true;
880 if ( type ==
"ULongLong" )
return true;
889 const QString type = t.toLower();
890 if ( type ==
"string" )
return "const QString &";
891 else if ( type ==
"stringlist" )
return "const QStringList &";
892 else if ( type ==
"font" )
return "const QFont &";
893 else if ( type ==
"rect" )
return "const QRect &";
894 else if ( type ==
"size" )
return "const QSize &";
895 else if ( type ==
"color" )
return "const QColor &";
896 else if ( type ==
"point" )
return "const QPoint &";
897 else if ( type ==
"int" )
return "int";
898 else if ( type ==
"uint" )
return "uint";
899 else if ( type ==
"bool" )
return "bool";
900 else if ( type ==
"double" )
return "double";
901 else if ( type ==
"datetime" )
return "const QDateTime &";
902 else if ( type ==
"longlong" )
return "qint64";
903 else if ( type ==
"ulonglong" )
return "quint64";
904 else if ( type ==
"intlist" )
return "const QList<int> &";
905 else if ( type ==
"enum" )
return "int";
906 else if ( type ==
"path" )
return "const QString &";
907 else if ( type ==
"pathlist" )
return "const QStringList &";
908 else if ( type ==
"password" )
return "const QString &";
909 else if ( type ==
"url" )
return "const KUrl &";
910 else if ( type ==
"urllist" )
return "const KUrl::List &";
912 cerr <<
"kconfig_compiler does not support type \""<< type <<
"\""<<endl;
922 const QString type = t.toLower();
923 if ( type ==
"string" )
return "QString";
924 else if ( type ==
"stringlist" )
return "QStringList";
925 else if ( type ==
"font" )
return "QFont";
926 else if ( type ==
"rect" )
return "QRect";
927 else if ( type ==
"size" )
return "QSize";
928 else if ( type ==
"color" )
return "QColor";
929 else if ( type ==
"point" )
return "QPoint";
930 else if ( type ==
"int" )
return "int";
931 else if ( type ==
"uint" )
return "uint";
932 else if ( type ==
"bool" )
return "bool";
933 else if ( type ==
"double" )
return "double";
934 else if ( type ==
"datetime" )
return "QDateTime";
935 else if ( type ==
"longlong" )
return "qint64";
936 else if ( type ==
"ulonglong" )
return "quint64";
937 else if ( type ==
"intlist" )
return "QList<int>";
938 else if ( type ==
"enum" )
return "int";
939 else if ( type ==
"path" )
return "QString";
940 else if ( type ==
"pathlist" )
return "QStringList";
941 else if ( type ==
"password" )
return "QString";
942 else if ( type ==
"url" )
return "KUrl";
943 else if ( type ==
"urllist" )
return "KUrl::List";
945 cerr<<
"kconfig_compiler does not support type \""<< type <<
"\""<<endl;
952 const QString type = t.toLower();
953 if ( type ==
"string" )
return "\"\"";
954 else if ( type ==
"stringlist" )
return "QStringList()";
955 else if ( type ==
"font" )
return "QFont()";
956 else if ( type ==
"rect" )
return "QRect()";
957 else if ( type ==
"size" )
return "QSize()";
958 else if ( type ==
"color" )
return "QColor(128, 128, 128)";
959 else if ( type ==
"point" )
return "QPoint()";
960 else if ( type ==
"int" )
return "0";
961 else if ( type ==
"uint" )
return "0";
962 else if ( type ==
"bool" )
return "false";
963 else if ( type ==
"double" )
return "0.0";
964 else if ( type ==
"datetime" )
return "QDateTime()";
965 else if ( type ==
"longlong" )
return "0";
966 else if ( type ==
"ulonglong" )
return "0";
967 else if ( type ==
"intlist" )
return "QList<int>()";
968 else if ( type ==
"enum" )
return "0";
969 else if ( type ==
"path" )
return "\"\"";
970 else if ( type ==
"pathlist" )
return "QStringList()";
971 else if ( type ==
"password" )
return "\"\"";
972 else if ( type ==
"url" )
return "KUrl()";
973 else if ( type ==
"urllist" )
return "KUrl::List()";
975 cerr<<
"Error, kconfig_compiler does not support the \""<< type <<
"\" type!"<<endl;
985 t.replace( 0, 1, t.left( 1 ).toUpper() );
992 if (cfg.itemAccessors)
996 fCap[0] = fCap[0].toUpper();
997 return " "+cfg.inherits+
"::Item"+
itemType( e->type() ) +
999 ( (!e->param().isEmpty())?(
QString(
"[%1]").arg(e->paramMax()+1)) :
QString()) +
1009 if (cfg.itemAccessors)
1011 if ( !cfg.dpointer )
1013 result =
'm' + e->name() +
"Item";
1014 result[1] = result[1].toUpper();
1018 result = e->name() +
"Item";
1019 result[0] = result[0].toLower();
1024 result =
"item" + e->name();
1025 result[4] = result[4].toUpper();
1033 if ( cfg.dpointer ) {
1034 result =
"d->"+
itemVar(e, cfg);
1046 "( currentGroup(), " + key +
", " +
varPath( name, cfg ) +
param;
1047 if ( type ==
"Enum" ) t +=
", values" + name;
1061 QString needle =
"$("+e->param()+
')';
1062 if (result.contains(needle))
1065 if (e->paramType() ==
"Enum")
1067 tmp = e->paramValues()[i];
1071 tmp = QString::number(i);
1074 result.replace(needle, tmp);
1085 it != parameters.constEnd(); ++it)
1090 tmp.sprintf(
"%%%d", i++);
1092 arguments +=
".arg( mParam"+(*it).name+
" )";
1095 if (arguments.isEmpty())
1096 return "QLatin1String( \""+group+
"\" )";
1098 return "QString( QLatin1String( \""+
paramString+
"\" ) )"+arguments;
1105 if (itemVarStr.isNull()) itemVarStr=
itemPath(e, cfg);
1106 if ( !e->label().isEmpty() ) {
1107 txt +=
" " + itemVarStr +
"->setLabel( ";
1108 if ( !e->labelContext().isEmpty() )
1109 txt +=
"i18nc(" +
quoteString(e->labelContext()) +
", ";
1112 if ( !e->param().isEmpty() )
1113 txt +=
quoteString(e->label().replace(
"$("+e->param()+
')', i));
1118 if ( !e->toolTip().isEmpty() ) {
1119 txt +=
" " + itemVarStr +
"->setToolTip( ";
1120 if ( !e->toolTipContext().isEmpty() )
1121 txt +=
"i18nc(" +
quoteString(e->toolTipContext()) +
", ";
1124 if ( !e->param().isEmpty() )
1125 txt +=
quoteString(e->toolTip().replace(
"$("+e->param()+
')', i));
1130 if ( !e->whatsThis().isEmpty() ) {
1131 txt +=
" " + itemVarStr +
"->setWhatsThis( ";
1132 if ( !e->whatsThisContext().isEmpty() )
1133 txt +=
"i18nc(" +
quoteString(e->whatsThisContext()) +
", ";
1136 if ( !e->param().isEmpty() )
1137 txt +=
quoteString(e->whatsThis().replace(
"$("+e->param()+
')', i));
1151 QTextStream out(&result, QIODevice::WriteOnly);
1154 bool useEnumType = cfg.useEnumTypes && t ==
"Enum";
1158 out <<
"static_cast<" <<
enumType(e, globalEnums) <<
">(";
1160 if (!e->param().isEmpty())
1175 QTextStream out(&result, QIODevice::WriteOnly);
1179 if (!e->minValue().isEmpty())
1181 if (e->minValue() !=
"0" || !
isUnsigned(t)) {
1182 out <<
"if (v < " << e->minValue() <<
")" << endl;
1185 out <<
": value \" << v << \" is less than the minimum value of ";
1186 out << e->minValue()<<
"\";" << endl;
1187 out <<
" v = " << e->minValue() <<
";" << endl;
1192 if (!e->maxValue().isEmpty())
1194 out << endl <<
"if (v > " << e->maxValue() <<
")" << endl;
1197 out <<
": value \" << v << \" is greater than the maximum value of ";
1198 out << e->maxValue()<<
"\";" << endl;
1199 out <<
" v = " << e->maxValue() <<
";" << endl;
1200 out <<
"}" << endl << endl;
1203 out <<
"if (!" <<
This <<
"isImmutable( QString::fromLatin1( \"";
1204 if (!e->param().isEmpty())
1206 out << e->paramName().replace(
"$("+e->param()+
")",
"%1") <<
"\" ).arg( ";
1207 if ( e->paramType() ==
"Enum" ) {
1208 out <<
"QLatin1String( ";
1210 if (cfg.globalEnums)
1211 out <<
enumName(e->param()) <<
"ToString[i]";
1213 out <<
enumName(e->param()) <<
"::enumToString[i]";
1227 out <<
" ))" << (!e->signalList().empty() ?
" {" :
"") << endl;
1229 if (!e->param().isEmpty())
1231 out <<
" = v;" << endl;
1233 if ( !e->signalList().empty() ) {
1234 foreach(
const Signal &signal, e->signalList()) {
1249 QTextStream out(&result, QIODevice::WriteOnly);
1252 if (!e->param().isEmpty()) {
1253 out <<
" switch (i) {" << endl;
1254 for (
int i = 0; i <= e->paramMax(); ++i) {
1255 if (!e->paramDefaultValue(i).isEmpty()) {
1256 out <<
" case " << i <<
": return " << e->paramDefaultValue(i) <<
';' << endl;
1259 out <<
" default:" << endl;
1260 out <<
" return " << e->defaultValue().replace(
"$("+e->param()+
')',
"i") <<
';' << endl;
1261 out <<
" }" << endl;
1263 out <<
" return " << e->defaultValue() <<
';';
1275 QTextStream out(&result, QIODevice::WriteOnly);
1277 out <<
"return " <<
itemPath(e, cfg);
1278 if (!e->param().isEmpty()) out <<
"[i]";
1288 QTextStream out(&result, QIODevice::WriteOnly);
1289 QTextStream in(&text, QIODevice::ReadOnly);
1291 while ( !in.atEnd() )
1293 currLine = in.readLine();
1294 if (!currLine.isEmpty())
1295 for (
int i=0; i < spaces; i++)
1297 out << currLine << endl;
1306 if ( !p_ns.isEmpty() ) {
1307 const QStringList nameSpaces = p_ns.split(
"::" );
1308 foreach (
const QString &ns, nameSpaces )
1309 p_out <<
"namespace " << ns <<
" {" << endl;
1318 if ( !p_ns.isEmpty() ) {
1319 const int namespaceCount = p_ns.count(
"::" ) + 1;
1320 for (
int i = 0; i < namespaceCount; ++i )
1321 p_out <<
"}" << endl;
1329 QCoreApplication app(argc, argv);
1333 QString directoryName, inputFilename, codegenFilename;
1334 parseArgs(app.arguments(), directoryName, inputFilename, codegenFilename);
1336 QString baseDir = directoryName;
1338 if (!baseDir.endsWith(
'/') && !baseDir.endsWith(
'\\'))
1340 if (!baseDir.endsWith(
'/'))
1342 baseDir.append(
"/");
1344 if (!codegenFilename.endsWith(QLatin1String(
".kcfgc")))
1346 cerr <<
"Codegen options file must have extension .kcfgc" << endl;
1349 QString baseName = QFileInfo(codegenFilename).fileName();
1350 baseName = baseName.left(baseName.length() - 6);
1352 CfgConfig cfg = CfgConfig( codegenFilename );
1354 QFile input( inputFilename );
1360 if ( !doc.setContent( &input, &errorMsg, &errorRow, &errorCol ) ) {
1361 cerr <<
"Unable to load document." << endl;
1362 cerr <<
"Parse error in " << inputFilename <<
", line " << errorRow <<
", col " << errorCol <<
": " << errorMsg << endl;
1366 QDomElement cfgElement = doc.documentElement();
1368 if ( cfgElement.isNull() ) {
1369 cerr <<
"No document in kcfg file" << endl;
1374 bool cfgFileNameArg =
false;
1378 bool hasSignals =
false;
1382 for ( QDomElement e = cfgElement.firstChildElement(); !e.isNull(); e = e.nextSiblingElement() ) {
1385 if ( tag ==
"include" ) {
1386 QString includeFile = e.text();
1387 if (!includeFile.isEmpty())
1388 includes.append(includeFile);
1390 }
else if ( tag ==
"kcfgfile" ) {
1391 cfgFileName = e.attribute(
"name" );
1392 cfgFileNameArg = e.attribute(
"arg" ).toLower() ==
"true";
1393 for( QDomElement e2 = e.firstChildElement(); !e2.isNull(); e2 = e2.nextSiblingElement() ) {
1394 if ( e2.tagName() ==
"parameter" ) {
1396 p.name = e2.attribute(
"name" );
1397 p.type = e2.attribute(
"type" );
1398 if (p.type.isEmpty())
1400 parameters.append( p );
1404 }
else if ( tag ==
"group" ) {
1405 QString group = e.attribute(
"name" );
1406 if ( group.isEmpty() ) {
1407 cerr <<
"Group without name" << endl;
1410 for( QDomElement e2 = e.firstChildElement(); !e2.isNull(); e2 = e2.nextSiblingElement() ) {
1411 if ( e2.tagName() !=
"entry" )
continue;
1412 CfgEntry *entry =
parseEntry( group, e2, cfg );
1413 if ( entry ) entries.append( entry );
1415 cerr <<
"Can not parse entry." << endl;
1420 else if ( tag ==
"signal" ) {
1421 QString signalName = e.attribute(
"name" );
1422 if ( signalName.isEmpty() ) {
1423 cerr <<
"Signal without name." << endl;
1427 theSignal.name = signalName;
1429 for( QDomElement e2 = e.firstChildElement(); !e2.isNull(); e2 = e2.nextSiblingElement() ) {
1430 if ( e2.tagName() ==
"argument") {
1431 SignalArguments argument;
1432 argument.type = e2.attribute(
"type");
1433 if ( argument.type.isEmpty() ) {
1434 cerr <<
"Signal argument without type." << endl;
1437 argument.variableName = e2.text();
1438 theSignal.arguments.append(argument);
1440 else if( e2.tagName() ==
"label") {
1441 theSignal.label = e2.text();
1444 signalList.append(theSignal);
1448 if ( cfg.className.isEmpty() ) {
1449 cerr <<
"Class name missing" << endl;
1453 if ( cfg.singleton && !parameters.isEmpty() ) {
1454 cerr <<
"Singleton class can not have parameters" << endl;
1458 if ( !cfgFileName.isEmpty() && cfgFileNameArg)
1460 cerr <<
"Having both a fixed filename and a filename as argument is not possible." << endl;
1464 if ( entries.isEmpty() ) {
1465 cerr <<
"No entries." << endl;
1470 for( cfg = entries.first(); cfg; cfg = entries.next() ) {
1475 hasSignals = !signalList.empty();
1476 QString headerFileName = baseName +
".h";
1477 QString implementationFileName = baseName +
".cpp";
1478 QString mocFileName = baseName +
".moc";
1481 QFile
header( baseDir + headerFileName );
1482 if ( !
header.open( QIODevice::WriteOnly ) ) {
1483 cerr <<
"Can not open '" << baseDir << headerFileName <<
"for writing." << endl;
1487 QTextStream h( &
header );
1489 h.setCodec(
"utf-8");
1490 h <<
"// This file is generated by kconfig_compiler from " << QFileInfo(inputFilename).fileName() <<
"." << endl;
1491 h <<
"// All changes you do to this file will be lost." << endl;
1493 h <<
"#ifndef " << ( !cfg.nameSpace.isEmpty() ?
QString (
QString(cfg.nameSpace).replace(
"::",
"_" ).toUpper() +
'_') :
"" )
1494 << cfg.className.toUpper() <<
"_H" << endl;
1495 h <<
"#define " << ( !cfg.nameSpace.isEmpty() ?
QString (
QString(cfg.nameSpace).replace(
"::",
"_" ).toUpper() +
'_') :
"" )
1496 << cfg.className.toUpper() <<
"_H" << endl << endl;
1499 QStringList::ConstIterator it;
1500 for( it = cfg.headerIncludes.constBegin(); it != cfg.headerIncludes.constEnd(); ++it ) {
1501 if ( (*it).startsWith(
'"') )
1502 h <<
"#include " << *it << endl;
1504 h <<
"#include <" << *it <<
">" << endl;
1507 if ( cfg.headerIncludes.count() > 0 ) h << endl;
1509 if ( !cfg.singleton && parameters.isEmpty() )
1510 h <<
"#include <kglobal.h>" << endl;
1512 if ( cfg.inherits==
"KCoreConfigSkeleton" ) {
1513 h <<
"#include <kcoreconfigskeleton.h>" << endl;
1515 h <<
"#include <kconfigskeleton.h>" << endl;
1518 h <<
"#include <kdebug.h>" << endl << endl;
1521 for( it = includes.constBegin(); it != includes.constEnd(); ++it ) {
1522 if ( (*it).startsWith(
'"') )
1523 h <<
"#include " << *it << endl;
1525 h <<
"#include <" << *it <<
">" << endl;
1532 h <<
"class " << cfg.className <<
"Private;" << endl << endl;
1535 h <<
"class " << cfg.visibility << cfg.className <<
" : public " << cfg.inherits << endl;
1540 h <<
" Q_OBJECT" << endl;
1541 h <<
" public:" << endl;
1545 for( itEntry = entries.constBegin(); itEntry != entries.constEnd(); ++itEntry ) {
1546 const CfgEntry::Choices &choices = (*itEntry)->choices();
1548 if ( !chlist.isEmpty() ) {
1551 for( itChoice = chlist.constBegin(); itChoice != chlist.constEnd(); ++itChoice ) {
1552 values.append( choices.prefix + (*itChoice).name );
1554 if ( choices.name().isEmpty() ) {
1555 if ( cfg.globalEnums ) {
1556 h <<
" enum " <<
enumName( (*itEntry)->name(), (*itEntry)->choices() ) <<
" { " << values.join(
", " ) <<
" };" << endl;
1559 h <<
" class " <<
enumName( (*itEntry)->name(), (*itEntry)->choices() ) << endl;
1561 h <<
" public:" << endl;
1562 h <<
" enum type { " << values.join(
", " ) <<
", COUNT };" << endl;
1565 }
else if ( !choices.external() ) {
1567 h <<
" enum " <<
enumName( (*itEntry)->name(), (*itEntry)->choices() ) <<
" { " << values.join(
", " ) <<
" };" << endl;
1570 const QStringList values = (*itEntry)->paramValues();
1571 if ( !values.isEmpty() ) {
1572 if ( cfg.globalEnums ) {
1576 h <<
" enum " <<
enumName( (*itEntry)->param() ) <<
" { " << values.join(
", " ) <<
" };" << endl;
1577 h <<
" static const char* const " <<
enumName( (*itEntry)->param() ) <<
"ToString[];" << endl;
1578 cppPreamble +=
"const char* const " + cfg.className +
"::" +
enumName( (*itEntry)->param() ) +
1579 "ToString[] = { \"" + values.join(
"\", \"" ) +
"\" };\n";
1581 h <<
" class " <<
enumName( (*itEntry)->param() ) << endl;
1583 h <<
" public:" << endl;
1584 h <<
" enum type { " << values.join(
", " ) <<
", COUNT };" << endl;
1585 h <<
" static const char* const enumToString[];" << endl;
1587 cppPreamble +=
"const char* const " + cfg.className +
"::" +
enumName( (*itEntry)->param() ) +
1588 "::enumToString[] = { \"" + values.join(
"\", \"" ) +
"\" };\n";
1593 h <<
"\n enum {" << endl;
1596 for ( it = signalList.constBegin(); it != itEnd; val <<= 1) {
1598 cerr <<
"Too many signals to create unique bit masks" << endl;
1601 Signal signal = *it;
1602 h <<
" " <<
signalEnumName(signal.name) <<
" = 0x" << hex << val;
1603 if ( ++it != itEnd )
1607 h <<
" };" << dec << endl;
1611 if ( !cfg.singleton ) {
1612 h <<
" " << cfg.className <<
"(";
1615 if(cfg.forceStringFilename)
1616 h <<
" const QString &cfgfilename"
1617 << (parameters.isEmpty() ?
" = QString()" :
", ");
1619 h <<
" KSharedConfig::Ptr config"
1620 << (parameters.isEmpty() ?
" = KGlobal::config()" :
", ");
1623 it != parameters.constEnd(); ++it)
1625 if (it != parameters.constBegin())
1627 h <<
" " <<
param((*it).type) <<
" " << (*it).name;
1631 h <<
" static " << cfg.className <<
" *self();" << endl;
1634 h <<
" static void instance(const QString& cfgfilename);" << endl;
1639 h <<
" ~" << cfg.className <<
"();" << endl << endl;
1642 if (cfg.staticAccessors)
1647 for( itEntry = entries.constBegin(); itEntry != entries.constEnd(); ++itEntry ) {
1648 QString n = (*itEntry)->name();
1649 QString t = (*itEntry)->type();
1652 if (cfg.allMutators || cfg.mutators.contains(n))
1654 h <<
" /**" << endl;
1655 h <<
" Set " << (*itEntry)->label() << endl;
1657 if (cfg.staticAccessors)
1658 h <<
" static" << endl;
1660 if (!(*itEntry)->param().isEmpty())
1661 h <<
cppType((*itEntry)->paramType()) <<
" i, ";
1662 if (cfg.useEnumTypes && t ==
"Enum")
1663 h <<
enumType(*itEntry, cfg.globalEnums);
1669 if ( !cfg.dpointer )
1671 h << endl <<
" {" << endl;
1682 h <<
" /**" << endl;
1683 h <<
" Get " << (*itEntry)->label() << endl;
1685 if (cfg.staticAccessors)
1686 h <<
" static" << endl;
1688 if (cfg.useEnumTypes && t ==
"Enum")
1689 h <<
enumType(*itEntry, cfg.globalEnums);
1693 if (!(*itEntry)->param().isEmpty())
1694 h <<
" " <<
cppType((*itEntry)->paramType()) <<
" i ";
1698 if ( !cfg.dpointer )
1700 h << endl <<
" {" << endl;
1710 if ((cfg.allDefaultGetters || cfg.defaultGetters.contains(n)) && !(*itEntry)->defaultValue().isEmpty()) {
1712 h <<
" /**" << endl;
1713 h <<
" Get " << (*itEntry)->label() <<
" default value" << endl;
1715 if (cfg.staticAccessors)
1716 h <<
" static" << endl;
1718 if (cfg.useEnumTypes && t ==
"Enum")
1719 h <<
enumType(*itEntry, cfg.globalEnums);
1723 if ( !(*itEntry)->param().isEmpty() )
1724 h <<
" " <<
cppType( (*itEntry)->paramType() ) <<
" i ";
1725 h <<
")" <<
Const << endl;
1728 if (cfg.useEnumTypes && t ==
"Enum")
1729 h <<
"static_cast<" <<
enumType(*itEntry, cfg.globalEnums) <<
">(";
1731 if ( !(*itEntry)->param().isEmpty() )
1734 if (cfg.useEnumTypes && t ==
"Enum")
1741 if ( cfg.itemAccessors ) {
1743 h <<
" /**" << endl;
1744 h <<
" Get Item object corresponding to " << n <<
"()"
1747 h <<
" Item" <<
itemType( (*itEntry)->type() ) <<
" *"
1749 if (!(*itEntry)->param().isEmpty()) {
1750 h <<
" " <<
cppType((*itEntry)->paramType()) <<
" i ";
1753 if ( !cfg.dpointer )
1755 h << endl <<
" {" << endl;
1773 foreach(
const Signal &signal, signalList) {
1775 if ( !signal.label.isEmpty() ) {
1776 h <<
" /**" << endl;
1777 h <<
" " << signal.label << endl;
1780 h <<
" void " << signal.name <<
"(";
1782 for ( it = signal.arguments.constBegin(); it != itEnd; ) {
1783 SignalArguments argument = *it;
1785 if ( cfg.useEnumTypes && argument.type ==
"Enum" ) {
1786 for (
int i = 0, end = entries.count(); i < end; ++i ) {
1787 if ( entries[i]->name() == argument.variableName ) {
1788 type =
enumType(entries[i], cfg.globalEnums);
1793 h << type <<
" " << argument.variableName;
1794 if ( ++it != itEnd ) {
1803 h <<
" protected:" << endl;
1806 if ( cfg.singleton ) {
1807 h <<
" " << cfg.className <<
"(";
1808 if ( cfgFileNameArg )
1809 h <<
"const QString& arg";
1811 h <<
" friend class " << cfg.className <<
"Helper;" << endl << endl;
1815 h <<
" virtual void usrWriteConfig();" << endl;
1819 if ( !cfg.memberVariables.isEmpty() && cfg.memberVariables !=
"private" && cfg.memberVariables !=
"dpointer") {
1820 h <<
" " << cfg.memberVariables <<
":" << endl;
1825 it != parameters.constEnd(); ++it)
1827 h <<
" " <<
cppType((*it).type) <<
" mParam" << (*it).name <<
";" << endl;
1830 if ( cfg.memberVariables !=
"dpointer" )
1833 for( itEntry = entries.constBegin(); itEntry != entries.constEnd(); ++itEntry ) {
1834 if ( (*itEntry)->group() != group ) {
1835 group = (*itEntry)->group();
1837 h <<
" // " << group << endl;
1839 h <<
" " <<
cppType( (*itEntry)->type() ) <<
" " <<
varName( (*itEntry)->name(), cfg );
1840 if ( !(*itEntry)->param().isEmpty() )
1842 h <<
QString(
"[%1]").arg( (*itEntry)->paramMax()+1 );
1846 if ( cfg.allDefaultGetters || cfg.defaultGetters.contains((*itEntry)->name()) )
1849 if (cfg.staticAccessors)
1852 if ( !(*itEntry)->param().isEmpty() )
1853 h <<
" " <<
cppType( (*itEntry)->paramType() ) <<
" i ";
1854 h <<
")" <<
Const <<
";" << endl;
1858 h << endl <<
" private:" << endl;
1859 if ( cfg.itemAccessors ) {
1860 for( itEntry = entries.constBegin(); itEntry != entries.constEnd(); ++itEntry ) {
1861 h <<
" Item" <<
itemType( (*itEntry)->type() ) <<
" *" <<
itemVar( *itEntry, cfg );
1862 if ( !(*itEntry)->param().isEmpty() ) h <<
QString(
"[%1]").arg( (*itEntry)->paramMax()+1 );
1867 h <<
" uint " <<
varName(
"settingsChanged", cfg) <<
";" << endl;
1873 h <<
" private:" << endl;
1874 for( itEntry = entries.constBegin(); itEntry != entries.constEnd(); ++itEntry ) {
1875 if ( cfg.allDefaultGetters || cfg.defaultGetters.contains((*itEntry)->name()) ) {
1877 if (cfg.staticAccessors)
1880 if ( !(*itEntry)->param().isEmpty() )
1881 h <<
" " <<
cppType( (*itEntry)->paramType() ) <<
" i ";
1882 h <<
")" <<
Const <<
";" << endl;
1885 h <<
" " + cfg.className +
"Private *d;" << endl;
1888 if (cfg.customAddons)
1890 h <<
" // Include custom additions" << endl;
1891 h <<
" #include \"" <<
filenameOnly(baseName) <<
"_addons.h\"" <<endl;
1894 h <<
"};" << endl << endl;
1898 h <<
"#endif" << endl << endl;
1903 QFile implementation( baseDir + implementationFileName );
1904 if ( !implementation.open( QIODevice::WriteOnly ) ) {
1905 cerr <<
"Can not open '" << implementationFileName <<
"for writing."
1910 QTextStream cpp( &implementation );
1912 cpp.setCodec(
"utf-8");
1913 cpp <<
"// This file is generated by kconfig_compiler from " << QFileInfo(inputFilename).fileName() <<
"." << endl;
1914 cpp <<
"// All changes you do to this file will be lost." << endl << endl;
1916 cpp <<
"#include \"" << headerFileName <<
"\"" << endl << endl;
1918 for( it = cfg.sourceIncludes.constBegin(); it != cfg.sourceIncludes.constEnd(); ++it ) {
1919 if ( (*it).startsWith(
'"') )
1920 cpp <<
"#include " << *it << endl;
1922 cpp <<
"#include <" << *it <<
">" << endl;
1925 if ( cfg.sourceIncludes.count() > 0 ) cpp << endl;
1927 if ( cfg.setUserTexts ) cpp <<
"#include <klocale.h>" << endl << endl;
1930 if ( cfg.singleton )
1931 cpp <<
"#include <kglobal.h>" << endl <<
"#include <QtCore/QFile>" << endl << endl;
1932 if ( cfg.singleton && cfgFileNameArg )
1933 cpp <<
"#include <kdebug.h>" << endl << endl;
1935 if ( !cfg.nameSpace.isEmpty() )
1936 cpp <<
"using namespace " << cfg.nameSpace <<
";" << endl << endl;
1944 cpp <<
"class " << cfg.className <<
"Private" << endl;
1946 cpp <<
" public:" << endl;
1947 for( itEntry = entries.constBegin(); itEntry != entries.constEnd(); ++itEntry ) {
1948 if ( (*itEntry)->group() != group ) {
1949 group = (*itEntry)->group();
1951 cpp <<
" // " << group << endl;
1953 cpp <<
" " <<
cppType( (*itEntry)->type() ) <<
" " <<
varName( (*itEntry)->name(), cfg );
1954 if ( !(*itEntry)->param().isEmpty() )
1956 cpp <<
QString(
"[%1]").arg( (*itEntry)->paramMax()+1 );
1960 cpp << endl <<
" // items" << endl;
1961 for( itEntry = entries.constBegin(); itEntry != entries.constEnd(); ++itEntry ) {
1962 cpp <<
" "+cfg.inherits+
"::Item" <<
itemType( (*itEntry)->type() ) <<
" *" <<
itemVar( *itEntry, cfg );
1963 if ( !(*itEntry)->param().isEmpty() ) cpp <<
QString(
"[%1]").arg( (*itEntry)->paramMax()+1 );
1967 cpp <<
" uint " <<
varName(
"settingsChanged", cfg) <<
";" << endl;
1970 cpp <<
"};" << endl << endl;
1975 if ( cfg.singleton ) {
1977 cpp <<
"class " << cfg.className <<
"Helper" << endl;
1979 cpp <<
" public:" << endl;
1980 cpp <<
" " << cfg.className <<
"Helper() : q(0) {}" << endl;
1981 cpp <<
" ~" << cfg.className <<
"Helper() { delete q; }" << endl;
1982 cpp <<
" " << cfg.className <<
" *q;" << endl;
1983 cpp <<
"};" << endl;
1985 cpp <<
"K_GLOBAL_STATIC(" << cfg.className <<
"Helper, s_global" << cfg.className <<
")" << endl;
1987 cpp << cfg.className <<
" *" << cfg.className <<
"::self()" << endl;
1989 if ( cfgFileNameArg ) {
1990 cpp <<
" if (!s_global" << cfg.className <<
"->q)" << endl;
1991 cpp <<
" kFatal() << \"you need to call " << cfg.className <<
"::instance before using\";" << endl;
1993 cpp <<
" if (!s_global" << cfg.className <<
"->q) {" << endl;
1994 cpp <<
" new " << cfg.className <<
';' << endl;
1995 cpp <<
" s_global" << cfg.className <<
"->q->readConfig();" << endl;
1996 cpp <<
" }" << endl << endl;
1998 cpp <<
" return s_global" << cfg.className <<
"->q;" << endl;
1999 cpp <<
"}" << endl << endl;
2001 if ( cfgFileNameArg ) {
2002 cpp <<
"void " << cfg.className <<
"::instance(const QString& cfgfilename)" << endl;
2004 cpp <<
" if (s_global" << cfg.className <<
"->q) {" << endl;
2005 cpp <<
" kDebug() << \"" << cfg.className <<
"::instance called after the first use - ignoring\";" << endl;
2006 cpp <<
" return;" << endl;
2007 cpp <<
" }" << endl;
2008 cpp <<
" new " << cfg.className <<
"(cfgfilename);" << endl;
2009 cpp <<
" s_global" << cfg.className <<
"->q->readConfig();" << endl;
2010 cpp <<
"}" << endl << endl;
2014 if ( !cppPreamble.isEmpty() )
2015 cpp << cppPreamble << endl;
2018 cpp << cfg.className <<
"::" << cfg.className <<
"( ";
2019 if ( cfgFileNameArg ) {
2020 if ( !cfg.singleton && ! cfg.forceStringFilename)
2021 cpp <<
" KSharedConfig::Ptr config";
2023 cpp <<
" const QString& config";
2024 cpp << (parameters.isEmpty() ?
" " :
", ");
2028 it != parameters.constEnd(); ++it)
2030 if (it != parameters.constBegin())
2032 cpp <<
" " <<
param((*it).type) <<
" " << (*it).name;
2034 cpp <<
" )" << endl;
2036 cpp <<
" : " << cfg.inherits <<
"(";
2037 if ( !cfgFileName.isEmpty() ) cpp <<
" QLatin1String( \"" << cfgFileName <<
"\" ";
2038 if ( cfgFileNameArg ) cpp <<
" config ";
2039 if ( !cfgFileName.isEmpty() ) cpp <<
") ";
2044 it != parameters.constEnd(); ++it)
2046 cpp <<
" , mParam" << (*it).name <<
"(" << (*it).name <<
")" << endl;
2049 if ( hasSignals && !cfg.dpointer )
2050 cpp <<
" , " <<
varName(
"settingsChanged", cfg) <<
"(0)" << endl;
2056 cpp <<
" d = new " + cfg.className +
"Private;" << endl;
2058 cpp <<
" " <<
varPath(
"settingsChanged", cfg) <<
" = 0;" << endl;
2062 if (cfg.singleton) {
2063 cpp <<
" Q_ASSERT(!s_global" << cfg.className <<
"->q);" << endl;
2064 cpp <<
" s_global" << cfg.className <<
"->q = this;" << endl;
2069 for( itEntry = entries.constBegin(); itEntry != entries.constEnd(); ++itEntry ) {
2070 if ( (*itEntry)->group() != group ) {
2071 if ( !group.isEmpty() ) cpp << endl;
2072 group = (*itEntry)->group();
2073 cpp <<
" setCurrentGroup( " <<
paramString(group, parameters) <<
" );" << endl << endl;
2077 if ( !(*itEntry)->code().isEmpty() ) {
2078 cpp << (*itEntry)->code() << endl;
2080 if ( (*itEntry)->type() ==
"Enum" ) {
2081 cpp <<
" QList<"+cfg.inherits+
"::ItemEnum::Choice2> values"
2082 << (*itEntry)->name() <<
";" << endl;
2085 for( it = choices.constBegin(); it != choices.constEnd(); ++it ) {
2086 cpp <<
" {" << endl;
2087 cpp <<
" "+cfg.inherits+
"::ItemEnum::Choice2 choice;" << endl;
2088 cpp <<
" choice.name = QLatin1String(\"" << (*it).name <<
"\");" << endl;
2089 if ( cfg.setUserTexts ) {
2090 if ( !(*it).label.isEmpty() ) {
2091 cpp <<
" choice.label = ";
2092 if ( !(*it).context.isEmpty() )
2093 cpp <<
"i18nc(" +
quoteString((*it).context) +
", ";
2098 if ( !(*it).toolTip.isEmpty() ) {
2099 cpp <<
" choice.toolTip = ";
2100 if ( !(*it).context.isEmpty() )
2101 cpp <<
"i18nc(" +
quoteString((*it).context) +
", ";
2104 cpp <<
quoteString((*it).toolTip) <<
");" << endl;
2106 if ( !(*it).whatsThis.isEmpty() ) {
2107 cpp <<
" choice.whatsThis = ";
2108 if ( !(*it).context.isEmpty() )
2109 cpp <<
"i18nc(" +
quoteString((*it).context) +
", ";
2112 cpp <<
quoteString((*it).whatsThis) <<
");" << endl;
2115 cpp <<
" values" << (*itEntry)->name() <<
".append( choice );" << endl;
2116 cpp <<
" }" << endl;
2123 if ( (*itEntry)->param().isEmpty() )
2126 cpp <<
" " <<
itemPath( *itEntry, cfg ) <<
" = "
2127 <<
newItem( (*itEntry)->type(), (*itEntry)->name(), key, (*itEntry)->defaultValue(), cfg ) << endl;
2129 if ( !(*itEntry)->minValue().isEmpty() )
2130 cpp <<
" " <<
itemPath( *itEntry, cfg ) <<
"->setMinValue(" << (*itEntry)->minValue() <<
");" << endl;
2131 if ( !(*itEntry)->maxValue().isEmpty() )
2132 cpp <<
" " <<
itemPath( *itEntry, cfg ) <<
"->setMaxValue(" << (*itEntry)->maxValue() <<
");" << endl;
2134 if ( cfg.setUserTexts )
2137 cpp <<
" addItem( " <<
itemPath( *itEntry, cfg );
2138 QString quotedName = (*itEntry)->name();
2140 if ( quotedName != key ) cpp <<
", QLatin1String( \"" << (*itEntry)->name() <<
"\" )";
2141 cpp <<
" );" << endl;
2146 for(
int i = 0; i <= (*itEntry)->paramMax(); i++)
2151 if ( !(*itEntry)->paramDefaultValue(i).isEmpty() )
2152 defaultStr = (*itEntry)->paramDefaultValue(i);
2153 else if ( !(*itEntry)->defaultValue().isEmpty() )
2154 defaultStr =
paramString( (*itEntry)->defaultValue(), (*itEntry), i );
2158 cpp <<
" " << itemVarStr <<
" = "
2159 <<
newItem( (*itEntry)->type(), (*itEntry)->name(),
paramString(key, *itEntry, i), defaultStr,cfg,
QString(
"[%1]").arg(i) )
2162 if ( cfg.setUserTexts )
2169 cpp <<
" addItem( " << itemVarStr <<
", QLatin1String( \"";
2170 if ( (*itEntry)->paramType()==
"Enum" )
2171 cpp << (*itEntry)->paramName().replace(
"$("+(*itEntry)->param()+
')',
"%1").arg((*itEntry)->paramValues()[i] );
2173 cpp << (*itEntry)->paramName().replace(
"$("+(*itEntry)->param()+
')',
"%1").arg(i);
2174 cpp <<
"\" ) );" << endl;
2179 cpp <<
"}" << endl << endl;
2184 for( itEntry = entries.constBegin(); itEntry != entries.constEnd(); ++itEntry ) {
2185 QString n = (*itEntry)->name();
2186 QString t = (*itEntry)->type();
2189 if (cfg.allMutators || cfg.mutators.contains(n))
2191 cpp <<
"void " <<
setFunction(n, cfg.className) <<
"( ";
2192 if ( !(*itEntry)->param().isEmpty() )
2193 cpp <<
cppType( (*itEntry)->paramType() ) <<
" i, ";
2194 if (cfg.useEnumTypes && t ==
"Enum")
2195 cpp <<
enumType(*itEntry, cfg.globalEnums);
2198 cpp <<
" v )" << endl;
2203 cpp <<
"}" << endl << endl;
2207 if (cfg.useEnumTypes && t ==
"Enum")
2208 cpp <<
enumType(*itEntry, cfg.globalEnums);
2211 cpp <<
" " <<
getFunction(n, cfg.className) <<
"(";
2212 if ( !(*itEntry)->param().isEmpty() )
2213 cpp <<
" " <<
cppType( (*itEntry)->paramType() ) <<
" i ";
2214 cpp <<
")" <<
Const << endl;
2219 cpp <<
"}" << endl << endl;
2224 if ( cfg.itemAccessors )
2227 cpp << cfg.inherits+
"::Item" <<
itemType( (*itEntry)->type() ) <<
" *"
2229 if ( !(*itEntry)->param().isEmpty() ) {
2230 cpp <<
" " <<
cppType( (*itEntry)->paramType() ) <<
" i ";
2243 for( itEntry = entries.constBegin(); itEntry != entries.constEnd(); ++itEntry ) {
2244 QString n = (*itEntry)->name();
2245 QString t = (*itEntry)->type();
2248 if (( cfg.allDefaultGetters || cfg.defaultGetters.contains(n) ) && !(*itEntry)->defaultValue().isEmpty() ) {
2250 if ( !(*itEntry)->param().isEmpty() )
2251 cpp <<
" " <<
cppType( (*itEntry)->paramType() ) <<
" i ";
2252 cpp <<
")" <<
Const << endl;
2255 cpp <<
"}" << endl << endl;
2260 cpp << cfg.className <<
"::~" << cfg.className <<
"()" << endl;
2262 if ( cfg.singleton ) {
2264 cpp <<
" delete d;" << endl;
2265 cpp <<
" if (!s_global" << cfg.className <<
".isDestroyed()) {" << endl;
2266 cpp <<
" s_global" << cfg.className <<
"->q = 0;" << endl;
2267 cpp <<
" }" << endl;
2269 cpp <<
"}" << endl << endl;
2272 cpp <<
"void " << cfg.className <<
"::" <<
"usrWriteConfig()" << endl;
2274 cpp <<
" " << cfg.inherits <<
"::usrWriteConfig();" << endl << endl;
2275 foreach(
const Signal &signal, signalList) {
2276 cpp <<
" if ( " <<
varPath(
"settingsChanged", cfg) <<
" & " <<
signalEnumName(signal.name) <<
" ) " << endl;
2277 cpp <<
" emit " << signal.name <<
"(";
2279 for ( it = signal.arguments.constBegin(); it != itEnd; ) {
2280 SignalArguments argument = *it;
2282 if ( cfg.useEnumTypes && argument.type ==
"Enum" ) {
2283 for (
int i = 0, end = entries.count(); i < end; ++i ) {
2284 if ( entries[i]->name() == argument.variableName ) {
2285 cpp <<
"static_cast<" <<
enumType(entries[i], cfg.globalEnums) <<
">(";
2291 cpp <<
varPath(argument.variableName, cfg);
2294 if ( ++it != itEnd )
2297 cpp <<
");" << endl << endl;
2299 cpp <<
" " <<
varPath(
"settingsChanged", cfg) <<
" = 0;" << endl;
2306 cpp <<
"#include \"" << mocFileName <<
"\"" << endl;
2311 qDeleteAll( entries );
2313 implementation.close();
static QString filenameOnly(const QString &path)
QString newItem(const QString &type, const QString &name, const QString &key, const QString &defaultValue, const CfgConfig &cfg, const QString ¶m=QString())
QString memberMutatorBody(CfgEntry *e, const CfgConfig &cfg)
static QString dumpNode(const QDomNode &node)
static QString itemDeclaration(const CfgEntry *e, const CfgConfig &cfg)
static QString setFunction(const QString &n, const QString &className=QString())
QRegExp * validNameRegexp
QString paramString(const QString &s, const CfgEntry *e, int i)
QString defaultValue(const QString &t)
static QString itemVar(const CfgEntry *e, const CfgConfig &cfg)
void endNamespaces(const QString &p_ns, QTextStream &p_out)
int main(int argc, char **argv)
QString memberGetDefaultBody(CfgEntry *e)
static QString enumTypeQualifier(const QString &n, const CfgEntry::Choices &c)
QString indent(QString text, int spaces)
static void preProcessDefault(QString &defaultValue, const QString &name, const QString &type, const CfgEntry::Choices &choices, QString &code, const CfgConfig &cfg)
static void parseArgs(const QStringList &args, QString &directory, QString &file1, QString &file2)
static QString getDefaultFunction(const QString &n, const QString &className=QString())
QString itemAccessorBody(CfgEntry *e, const CfgConfig &cfg)
CfgEntry * parseEntry(const QString &group, const QDomElement &element, const CfgConfig &cfg)
static QString signalEnumName(const QString &signalName)
static QString varPath(const QString &n, const CfgConfig &cfg)
QString itemType(const QString &type)
static QString enumName(const QString &n)
static bool isUnsigned(const QString &type)
static QString quoteString(const QString &s)
static QString itemPath(const CfgEntry *e, const CfgConfig &cfg)
void beginNamespaces(const QString &p_ns, QTextStream &p_out)
QString cppType(const QString &t)
Actual C++ storage type for given type.
QString userTextsFunctions(CfgEntry *e, const CfgConfig &cfg, QString itemVarStr=QString(), QString i=QString())
QString memberAccessorBody(CfgEntry *e, bool globalEnums, const CfgConfig &cfg)
static QString literalString(const QString &s)
static QString enumType(const CfgEntry *e, bool globalEnums)
QString param(const QString &t)
Return parameter declaration for given type.
static void addQuotes(QString &s)
static QString varName(const QString &n, const CfgConfig &cfg)
static QString getFunction(const QString &n, const QString &className=QString())