2 ******************************************************************************
4 * @file uavobjectgeneratorpython.cpp
5 * @author The OpenPilot Team, http://www.openpilot.org Copyright (C) 2010.
6 * @brief produce python code for uavobjects
8 * @see The GNU Public License (GPL) Version 3
10 *****************************************************************************/
12 * This program is free software; you can redistribute it and/or modify
13 * it under the terms of the GNU General Public License as published by
14 * the Free Software Foundation; either version 3 of the License, or
15 * (at your option) any later version.
17 * This program is distributed in the hope that it will be useful, but
18 * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
19 * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
22 * You should have received a copy of the GNU General Public License along
23 * with this program; if not, write to the Free Software Foundation, Inc.,
24 * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
27 #include "uavobjectgeneratorpython.h"
30 bool UAVObjectGeneratorPython::generate(UAVObjectParser
*parser
, QString templatepath
, QString outputpath
)
32 // Load template and setup output directory
33 pythonCodePath
= QDir(templatepath
+ QString("flight/modules/FlightPlan/lib"));
34 pythonOutputPath
= QDir(outputpath
);
35 pythonOutputPath
.mkpath(pythonOutputPath
.absolutePath());
36 pythonCodeTemplate
= readFile(pythonCodePath
.absoluteFilePath("uavobject.pyt.template"));
37 if (pythonCodeTemplate
.isEmpty()) {
38 std::cerr
<< "Problem reading python templates" << endl
;
42 // Process each object
43 for (int objidx
= 0; objidx
< parser
->getNumObjects(); ++objidx
) {
44 ObjectInfo
*info
= parser
->getObjectByIndex(objidx
);
48 return true; // if we come here everything should be fine
52 * Generate the python object files
54 bool UAVObjectGeneratorPython::process_object(ObjectInfo
*info
)
60 // Prepare output strings
61 QString outCode
= pythonCodeTemplate
;
63 // Replace common tags
64 replaceCommonTags(outCode
, info
);
66 // Replace the ($DATAFIELDS) tag
68 for (int n
= 0; n
< info
->fields
.length(); ++n
) {
70 datafields
.append(QString("# Field %1 definition\n").arg(info
->fields
[n
]->name
));
71 datafields
.append(QString("class %1Field(UAVObjectField):\n").arg(info
->fields
[n
]->name
));
72 // Only for enum types
73 if (info
->fields
[n
]->type
== FIELDTYPE_ENUM
) {
74 datafields
.append(QString(" # Enumeration options\n"));
75 // Go through each option
76 QStringList options
= info
->fields
[n
]->options
;
77 for (int m
= 0; m
< options
.length(); ++m
) {
78 QString name
= options
[m
].toUpper().replace(QRegExp(ENUM_SPECIAL_CHARS
), "");
79 if (name
[0].isDigit()) {
80 name
= QString("N%1").arg(name
);
82 datafields
.append(QString(" %1 = %2\n").arg(name
).arg(m
));
85 // Generate element names (only if field has more than one element)
86 if (info
->fields
[n
]->numElements
> 1 && !info
->fields
[n
]->defaultElementNames
) {
87 datafields
.append(QString(" # Array element names\n"));
88 // Go through the element names
89 QStringList elemNames
= info
->fields
[n
]->elementNames
;
90 for (int m
= 0; m
< elemNames
.length(); ++m
) {
91 QString name
= elemNames
[m
].toUpper().replace(QRegExp(ENUM_SPECIAL_CHARS
), "");
92 if (name
[0].isDigit()) {
93 name
= QString("N%1").arg(name
);
95 datafields
.append(QString(" %1 = %2\n").arg(name
).arg(m
));
99 datafields
.append(QString(" def __init__(self):\n"));
100 datafields
.append(QString(" UAVObjectField.__init__(self, %1, %2)\n\n").arg(info
->fields
[n
]->type
).arg(info
->fields
[n
]->numElements
));
102 outCode
.replace(QString("$(DATAFIELDS)"), datafields
);
104 // Replace the $(DATAFIELDINIT) tag
106 for (int n
= 0; n
< info
->fields
.length(); ++n
) {
107 fields
.append(QString(" self.%1 = %1Field()\n").arg(info
->fields
[n
]->name
));
108 fields
.append(QString(" self.addField(self.%1)\n").arg(info
->fields
[n
]->name
));
110 outCode
.replace(QString("$(DATAFIELDINIT)"), fields
);
112 // Write the Python code
113 bool res
= writeFileIfDifferent(pythonOutputPath
.absolutePath() + "/" + info
->namelc
+ ".py", outCode
);
115 cout
<< "Error: Could not write Python output files" << endl
;