comparison generator/cppheadergenerator.cpp @ 1:e78566595089

initial import
author mandel
date Mon, 11 May 2009 16:01:50 +0000
parents
children e747af2e6b46
comparison
equal deleted inserted replaced
0:36fb74dc547d 1:e78566595089
1 /****************************************************************************
2 **
3 ** Copyright (C) 1992-2008 Nokia. All rights reserved.
4 **
5 ** This file is part of Qt Jambi.
6 **
7 ** * Commercial Usage
8 * Licensees holding valid Qt Commercial licenses may use this file in
9 * accordance with the Qt Commercial License Agreement provided with the
10 * Software or, alternatively, in accordance with the terms contained in
11 * a written agreement between you and Nokia.
12 *
13 *
14 * GNU General Public License Usage
15 * Alternatively, this file may be used under the terms of the GNU
16 * General Public License versions 2.0 or 3.0 as published by the Free
17 * Software Foundation and appearing in the file LICENSE.GPL included in
18 * the packaging of this file. Please review the following information
19 * to ensure GNU General Public Licensing requirements will be met:
20 * http://www.fsf.org/licensing/licenses/info/GPLv2.html and
21 * http://www.gnu.org/copyleft/gpl.html. In addition, as a special
22 * exception, Nokia gives you certain additional rights. These rights
23 * are described in the Nokia Qt GPL Exception version 1.2, included in
24 * the file GPL_EXCEPTION.txt in this package.
25 *
26 * Qt for Windows(R) Licensees
27 * As a special exception, Nokia, as the sole copyright holder for Qt
28 * Designer, grants users of the Qt/Eclipse Integration plug-in the
29 * right for the Qt/Eclipse Integration to link to functionality
30 * provided by Qt Designer and its related libraries.
31 *
32 *
33 * If you are unsure which license is appropriate for your use, please
34 * contact the sales department at qt-sales@nokia.com.
35
36 **
37 ** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
38 ** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
39 **
40 ****************************************************************************/
41
42 #include "cppheadergenerator.h"
43
44 #include <QtCore/QDir>
45
46 #include <qdebug.h>
47
48 QString CppHeaderGenerator::fileNameForClass(const AbstractMetaClass *java_class) const
49 {
50 return QString("%1_shell.h").arg(java_class->name());
51 }
52
53 void CppHeaderGenerator::writeFieldAccessors(QTextStream &s, const AbstractMetaField *java_field)
54 {
55 Q_ASSERT(java_field->isProtected());
56
57 const AbstractMetaFunction *setter = java_field->setter();
58 const AbstractMetaFunction *getter = java_field->getter();
59
60 // qtd2
61 if(notWrappedYet(getter))
62 return;
63
64 if (getter->isModifiedRemoved(TypeSystem::ShellCode))
65 return;
66
67 s << " ";
68 writeFunctionSignature(s, getter, 0, QString(), Option(ShowStatic));
69 s << ";" << endl;
70
71 // qtd2
72 if(notWrappedYet(setter))
73 return;
74
75 if (!java_field->type()->isConstant()) {
76 if (setter->isModifiedRemoved(TypeSystem::ShellCode))
77 return;
78
79 s << " ";
80 writeFunctionSignature(s, setter, 0, QString(), Option(ShowStatic));
81 s << ";" << endl;
82 }
83 }
84
85 void CppHeaderGenerator::writeSignalWrapper(QTextStream &s, const AbstractMetaFunction *signal)
86 {
87 s << " ";
88 writeFunctionSignature(s, signal, 0, signalWrapperPrefix(),
89 Option(NormalizeAndFixTypeSignature | OriginalName | OriginalTypeDescription | IncludeDefaultExpression));
90 s << ";" << endl;
91 }
92
93 void CppHeaderGenerator::writeSignalWrappers(QTextStream &s, const AbstractMetaClass *java_class)
94 {
95 AbstractMetaFunctionList signal_funcs = signalFunctions(java_class);
96 if (signal_funcs.size() > 0) {
97 s << endl << "public slots:" << endl;
98 foreach (const AbstractMetaFunction *signal, signal_funcs) {
99 writeSignalWrapper(s, signal);
100 }
101 }
102 }
103
104 void CppHeaderGenerator::writeWrapperClass(QTextStream &s, const AbstractMetaClass *java_class)
105 {
106 AbstractMetaFunctionList signal_functions =
107 java_class->queryFunctions(AbstractMetaClass::Signals | AbstractMetaClass::Visible | AbstractMetaClass::NotRemovedFromTargetLang);
108 if (signal_functions.size() == 0)
109 return ;
110
111 s << "class QtJambi_SignalWrapper_" << java_class->name() << ": public QObject" << endl
112 << "{" << endl
113 << " Q_OBJECT" << endl;
114 writeSignalWrappers(s, java_class);
115 s << endl << "public:" << endl
116 << " QtJambiSignalInfo m_signals[" << signal_functions.size() << "];" << endl
117 << " QtJambiLink *link;" << endl
118 << "};" << endl << endl;
119 }
120
121 void CppHeaderGenerator::write(QTextStream &s, const AbstractMetaClass *java_class)
122 {
123 QString include_block = java_class->name().toUpper() + "_SHELL_H";
124
125 s << "#ifndef " << include_block << endl
126 << "#define " << include_block << endl << endl
127 // << "#include <qtjambi_core.h>" << endl
128 << "#include <QtCore/QHash>" << endl
129 << "#include <QObjectEntity.h>" << endl;
130
131 Include inc = java_class->typeEntry()->include();
132 s << "#include ";
133 if (inc.type == Include::IncludePath)
134 s << "<";
135 else
136 s << "\"";
137 s << inc.name;
138 if (inc.type == Include::IncludePath)
139 s << ">";
140 else
141 s << "\"";
142 s << endl << endl;
143
144 IncludeList list = java_class->typeEntry()->extraIncludes();
145 qSort(list.begin(), list.end());
146 foreach (const Include &inc, list) {
147 if (inc.type == Include::TargetLangImport)
148 continue;
149
150 s << "#include ";
151 if (inc.type == Include::LocalPath)
152 s << "\"";
153 else
154 s << "<";
155
156 s << inc.name;
157
158 if (inc.type == Include::LocalPath)
159 s << "\"";
160 else
161 s << ">";
162
163 s << endl;
164 }
165
166 /* qtd writeForwardDeclareSection(s, java_class);
167
168 writeWrapperClass(s, java_class);
169 */
170 s << endl;
171 QString pro_file_name = java_class->package().replace(".", "_") + "/" + java_class->package().replace(".", "_") + ".pri";
172
173 if (!java_class->generateShellClass()) {
174 s << "#endif" << endl << endl;
175 priGenerator->addHeader(pro_file_name, fileNameForClass(java_class));
176 return ;
177 }
178
179 s << "class " << shellClassName(java_class)
180 << " : public " << java_class->qualifiedCppName();
181 if (java_class->hasVirtualFunctions())
182 s << ", public Qtd_QObjectEntity";
183 s << endl << "{" << endl;
184
185 if (java_class->isQObject()) {
186 s << "public:" << endl
187 << " Q_OBJECT_CHECK" << endl;
188 // << " mutable const QMetaObject *m_meta_object;" << endl;
189
190 /* if (java_class->hasVirtualSlots()) {
191 s << " mutable QHash<int,int> m_map;" << endl;
192 }
193 */
194 s // << " const QMetaObject *metaObject() const;" << endl
195 // << " void *qt_metacast(const char *);" << endl
196 // << " QT_TR_FUNCTIONS" << endl
197 << " virtual int qt_metacall(QMetaObject::Call, int, void **);" << endl
198 << "private:" << endl;
199 }
200
201
202 s << "public:" << endl;
203 // constructor
204 foreach (const AbstractMetaFunction *function, java_class->functions()) {
205 if (function->isConstructor() && !function->isPrivate())
206 writeFunction(s, function);
207 }
208
209 s << " ~" << shellClassName(java_class) << "();" << endl;
210 s << endl;
211
212 // All functions in original class that should be reimplemented in shell class
213 AbstractMetaFunctionList shell_functions = java_class->functionsInShellClass();
214 foreach (const AbstractMetaFunction *function, shell_functions) {
215 if(notWrappedYet(function))
216 continue;
217 writeFunction(s, function);
218 }
219
220 // Public call throughs for protected functions
221 AbstractMetaFunctionList public_overrides = java_class->publicOverrideFunctions();
222 foreach (const AbstractMetaFunction *function, public_overrides) {
223 if(notWrappedYet(function))
224 continue;
225 writePublicFunctionOverride(s, function);
226 }
227
228 // Override all virtual functions to get the decision on static/virtual call
229 AbstractMetaFunctionList virtual_functions = java_class->virtualOverrideFunctions();
230 foreach (const AbstractMetaFunction *function, virtual_functions) {
231 if(notWrappedYet(function))
232 continue;
233
234 writeVirtualFunctionOverride(s, function);
235 }
236
237 // Field accessors
238 foreach (const AbstractMetaField *field, java_class->fields()) {
239 if (field->isProtected())
240 writeFieldAccessors(s, field);
241 }
242 /* qtd
243 writeVariablesSection(s, java_class);
244 */
245 writeInjectedCode(s, java_class);
246
247 s << "};" << endl << endl
248 << "#endif // " << include_block << endl;
249
250 priGenerator->addHeader(pro_file_name, fileNameForClass(java_class));
251 }
252
253
254 /*!
255 Writes out declarations of virtual C++ functions so that they
256 can be reimplemented from the java side.
257 */
258 void CppHeaderGenerator::writeFunction(QTextStream &s, const AbstractMetaFunction *java_function)
259 {
260 if (java_function->isModifiedRemoved(TypeSystem::ShellCode))
261 return;
262
263 s << " ";
264 writeFunctionSignature(s, java_function, 0, QString(), Option(OriginalName | ShowStatic));
265 s << ";" << endl;
266 }
267
268 void CppHeaderGenerator::writePublicFunctionOverride(QTextStream &s,
269 const AbstractMetaFunction *java_function)
270 {
271 s << " ";
272 writeFunctionSignature(s, java_function, 0, "__public_", Option(EnumAsInts | ShowStatic | UnderscoreSpaces));
273 s << ";" << endl;
274 }
275
276
277 void CppHeaderGenerator::writeVirtualFunctionOverride(QTextStream &s,
278 const AbstractMetaFunction *java_function)
279 {
280 if (java_function->isModifiedRemoved(TypeSystem::NativeCode))
281 return;
282
283 s << " ";
284 writeFunctionSignature(s, java_function, 0, "__override_", Option(EnumAsInts | ShowStatic | UnderscoreSpaces), QString());
285 s << ";" << endl;
286 }
287
288
289 void CppHeaderGenerator::writeForwardDeclareSection(QTextStream &s, const AbstractMetaClass *)
290 {
291 s << endl
292 << "class QtJambiFunctionTable;" << endl
293 << "class QtJambiLink;" << endl;
294 }
295
296
297 void CppHeaderGenerator::writeVariablesSection(QTextStream &s, const AbstractMetaClass *)
298 {
299 s << endl
300 << " QtJambiFunctionTable *m_vtable;" << endl
301 << " QtJambiLink *m_link;" << endl;
302 }
303
304 void CppHeaderGenerator::writeInjectedCode(QTextStream &s, const AbstractMetaClass *java_class)
305 {
306 CodeSnipList code_snips = java_class->typeEntry()->codeSnips();
307 foreach (const CodeSnip &cs, code_snips) {
308 if (cs.language == TypeSystem::ShellDeclaration) {
309 s << cs.code() << endl;
310 }
311 }
312 }