Absolute File Name: | /home/opencoverage/opencoverage/guest-scripts/qtdeclarative/src/qtdeclarative/src/qml/jsapi/qjsengine.cpp |
Source code | Switch to Preprocessed file |
Line | Source | Count | ||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
1 | /**************************************************************************** | - | ||||||||||||
2 | ** | - | ||||||||||||
3 | ** Copyright (C) 2016 The Qt Company Ltd. | - | ||||||||||||
4 | ** Contact: https://www.qt.io/licensing/ | - | ||||||||||||
5 | ** | - | ||||||||||||
6 | ** This file is part of the QtQml module of the Qt Toolkit. | - | ||||||||||||
7 | ** | - | ||||||||||||
8 | ** $QT_BEGIN_LICENSE:LGPL$ | - | ||||||||||||
9 | ** Commercial License Usage | - | ||||||||||||
10 | ** Licensees holding valid commercial Qt licenses may use this file in | - | ||||||||||||
11 | ** accordance with the commercial license agreement provided with the | - | ||||||||||||
12 | ** Software or, alternatively, in accordance with the terms contained in | - | ||||||||||||
13 | ** a written agreement between you and The Qt Company. For licensing terms | - | ||||||||||||
14 | ** and conditions see https://www.qt.io/terms-conditions. For further | - | ||||||||||||
15 | ** information use the contact form at https://www.qt.io/contact-us. | - | ||||||||||||
16 | ** | - | ||||||||||||
17 | ** GNU Lesser General Public License Usage | - | ||||||||||||
18 | ** Alternatively, this file may be used under the terms of the GNU Lesser | - | ||||||||||||
19 | ** General Public License version 3 as published by the Free Software | - | ||||||||||||
20 | ** Foundation and appearing in the file LICENSE.LGPL3 included in the | - | ||||||||||||
21 | ** packaging of this file. Please review the following information to | - | ||||||||||||
22 | ** ensure the GNU Lesser General Public License version 3 requirements | - | ||||||||||||
23 | ** will be met: https://www.gnu.org/licenses/lgpl-3.0.html. | - | ||||||||||||
24 | ** | - | ||||||||||||
25 | ** GNU General Public License Usage | - | ||||||||||||
26 | ** Alternatively, this file may be used under the terms of the GNU | - | ||||||||||||
27 | ** General Public License version 2.0 or (at your option) the GNU General | - | ||||||||||||
28 | ** Public license version 3 or any later version approved by the KDE Free | - | ||||||||||||
29 | ** Qt Foundation. The licenses are as published by the Free Software | - | ||||||||||||
30 | ** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3 | - | ||||||||||||
31 | ** included in the packaging of this file. Please review the following | - | ||||||||||||
32 | ** information to ensure the GNU General Public License requirements will | - | ||||||||||||
33 | ** be met: https://www.gnu.org/licenses/gpl-2.0.html and | - | ||||||||||||
34 | ** https://www.gnu.org/licenses/gpl-3.0.html. | - | ||||||||||||
35 | ** | - | ||||||||||||
36 | ** $QT_END_LICENSE$ | - | ||||||||||||
37 | ** | - | ||||||||||||
38 | ****************************************************************************/ | - | ||||||||||||
39 | - | |||||||||||||
40 | #include "qjsengine.h" | - | ||||||||||||
41 | #include "qjsengine_p.h" | - | ||||||||||||
42 | #include "qjsvalue.h" | - | ||||||||||||
43 | #include "qjsvalue_p.h" | - | ||||||||||||
44 | #include "private/qv8engine_p.h" | - | ||||||||||||
45 | - | |||||||||||||
46 | #include "private/qv4engine_p.h" | - | ||||||||||||
47 | #include "private/qv4mm_p.h" | - | ||||||||||||
48 | #include "private/qv4globalobject_p.h" | - | ||||||||||||
49 | #include "private/qv4script_p.h" | - | ||||||||||||
50 | #include "private/qv4runtime_p.h" | - | ||||||||||||
51 | #include <private/qqmlbuiltinfunctions_p.h> | - | ||||||||||||
52 | #include <private/qqmldebugconnector_p.h> | - | ||||||||||||
53 | #include <private/qv4qobjectwrapper_p.h> | - | ||||||||||||
54 | #include <private/qv4stackframe_p.h> | - | ||||||||||||
55 | - | |||||||||||||
56 | #include <QtCore/qdatetime.h> | - | ||||||||||||
57 | #include <QtCore/qmetaobject.h> | - | ||||||||||||
58 | #include <QtCore/qstringlist.h> | - | ||||||||||||
59 | #include <QtCore/qvariant.h> | - | ||||||||||||
60 | #include <QtCore/qdatetime.h> | - | ||||||||||||
61 | - | |||||||||||||
62 | #include <QtCore/qcoreapplication.h> | - | ||||||||||||
63 | #include <QtCore/qdir.h> | - | ||||||||||||
64 | #include <QtCore/qfile.h> | - | ||||||||||||
65 | #include <QtCore/qfileinfo.h> | - | ||||||||||||
66 | #include <QtCore/qpluginloader.h> | - | ||||||||||||
67 | #include <qthread.h> | - | ||||||||||||
68 | #include <qmutex.h> | - | ||||||||||||
69 | #include <qwaitcondition.h> | - | ||||||||||||
70 | #include <private/qqmlglobal_p.h> | - | ||||||||||||
71 | #include <qqmlengine.h> | - | ||||||||||||
72 | - | |||||||||||||
73 | #undef Q_D | - | ||||||||||||
74 | #undef Q_Q | - | ||||||||||||
75 | #define Q_D(blah) | - | ||||||||||||
76 | #define Q_Q(blah) | - | ||||||||||||
77 | - | |||||||||||||
78 | Q_DECLARE_METATYPE(QList<int>) | - | ||||||||||||
79 | - | |||||||||||||
80 | /*! | - | ||||||||||||
81 | \since 5.0 | - | ||||||||||||
82 | \class QJSEngine | - | ||||||||||||
83 | \reentrant | - | ||||||||||||
84 | - | |||||||||||||
85 | \brief The QJSEngine class provides an environment for evaluating JavaScript code. | - | ||||||||||||
86 | - | |||||||||||||
87 | \ingroup qtjavascript | - | ||||||||||||
88 | \inmodule QtQml | - | ||||||||||||
89 | - | |||||||||||||
90 | \section1 Evaluating Scripts | - | ||||||||||||
91 | - | |||||||||||||
92 | Use evaluate() to evaluate script code. | - | ||||||||||||
93 | - | |||||||||||||
94 | \snippet code/src_script_qjsengine.cpp 0 | - | ||||||||||||
95 | - | |||||||||||||
96 | evaluate() returns a QJSValue that holds the result of the | - | ||||||||||||
97 | evaluation. The QJSValue class provides functions for converting | - | ||||||||||||
98 | the result to various C++ types (e.g. QJSValue::toString() | - | ||||||||||||
99 | and QJSValue::toNumber()). | - | ||||||||||||
100 | - | |||||||||||||
101 | The following code snippet shows how a script function can be | - | ||||||||||||
102 | defined and then invoked from C++ using QJSValue::call(): | - | ||||||||||||
103 | - | |||||||||||||
104 | \snippet code/src_script_qjsengine.cpp 1 | - | ||||||||||||
105 | - | |||||||||||||
106 | As can be seen from the above snippets, a script is provided to the | - | ||||||||||||
107 | engine in the form of a string. One common way of loading scripts is | - | ||||||||||||
108 | by reading the contents of a file and passing it to evaluate(): | - | ||||||||||||
109 | - | |||||||||||||
110 | \snippet code/src_script_qjsengine.cpp 2 | - | ||||||||||||
111 | - | |||||||||||||
112 | Here we pass the name of the file as the second argument to | - | ||||||||||||
113 | evaluate(). This does not affect evaluation in any way; the second | - | ||||||||||||
114 | argument is a general-purpose string that is stored in the \c Error | - | ||||||||||||
115 | object for debugging purposes. | - | ||||||||||||
116 | - | |||||||||||||
117 | \section1 Engine Configuration | - | ||||||||||||
118 | - | |||||||||||||
119 | The globalObject() function returns the \b {Global Object} | - | ||||||||||||
120 | associated with the script engine. Properties of the Global Object | - | ||||||||||||
121 | are accessible from any script code (i.e. they are global | - | ||||||||||||
122 | variables). Typically, before evaluating "user" scripts, you will | - | ||||||||||||
123 | want to configure a script engine by adding one or more properties | - | ||||||||||||
124 | to the Global Object: | - | ||||||||||||
125 | - | |||||||||||||
126 | \snippet code/src_script_qjsengine.cpp 3 | - | ||||||||||||
127 | - | |||||||||||||
128 | Adding custom properties to the scripting environment is one of the | - | ||||||||||||
129 | standard means of providing a scripting API that is specific to your | - | ||||||||||||
130 | application. Usually these custom properties are objects created by | - | ||||||||||||
131 | the newQObject() or newObject() functions. | - | ||||||||||||
132 | - | |||||||||||||
133 | \section1 Script Exceptions | - | ||||||||||||
134 | - | |||||||||||||
135 | evaluate() can throw a script exception (e.g. due to a syntax | - | ||||||||||||
136 | error). If it does, then evaluate() returns the value that was thrown | - | ||||||||||||
137 | (typically an \c{Error} object). Use \l QJSValue::isError() to check | - | ||||||||||||
138 | for exceptions. | - | ||||||||||||
139 | - | |||||||||||||
140 | For detailed information about the error, use \l QJSValue::toString() to | - | ||||||||||||
141 | obtain an error message, and use \l QJSValue::property() to query the | - | ||||||||||||
142 | properties of the \c Error object. The following properties are available: | - | ||||||||||||
143 | - | |||||||||||||
144 | \list | - | ||||||||||||
145 | \li \c name | - | ||||||||||||
146 | \li \c message | - | ||||||||||||
147 | \li \c fileName | - | ||||||||||||
148 | \li \c lineNumber | - | ||||||||||||
149 | \li \c stack | - | ||||||||||||
150 | \endlist | - | ||||||||||||
151 | - | |||||||||||||
152 | \snippet code/src_script_qjsengine.cpp 4 | - | ||||||||||||
153 | - | |||||||||||||
154 | \section1 Script Object Creation | - | ||||||||||||
155 | - | |||||||||||||
156 | Use newObject() to create a JavaScript object; this is the | - | ||||||||||||
157 | C++ equivalent of the script statement \c{new Object()}. You can use | - | ||||||||||||
158 | the object-specific functionality in QJSValue to manipulate the | - | ||||||||||||
159 | script object (e.g. QJSValue::setProperty()). Similarly, use | - | ||||||||||||
160 | newArray() to create a JavaScript array object. | - | ||||||||||||
161 | - | |||||||||||||
162 | \section1 QObject Integration | - | ||||||||||||
163 | - | |||||||||||||
164 | Use newQObject() to wrap a QObject (or subclass) | - | ||||||||||||
165 | pointer. newQObject() returns a proxy script object; properties, | - | ||||||||||||
166 | children, and signals and slots of the QObject are available as | - | ||||||||||||
167 | properties of the proxy object. No binding code is needed because it | - | ||||||||||||
168 | is done dynamically using the Qt meta object system. | - | ||||||||||||
169 | - | |||||||||||||
170 | \snippet code/src_script_qjsengine.cpp 5 | - | ||||||||||||
171 | - | |||||||||||||
172 | Use newQMetaObject() to wrap a QMetaObject; this gives you a | - | ||||||||||||
173 | "script representation" of a QObject-based class. newQMetaObject() | - | ||||||||||||
174 | returns a proxy script object; enum values of the class are available | - | ||||||||||||
175 | as properties of the proxy object. | - | ||||||||||||
176 | - | |||||||||||||
177 | Constructors exposed to the meta-object system (using Q_INVOKABLE) can be | - | ||||||||||||
178 | called from the script to create a new QObject instance with | - | ||||||||||||
179 | JavaScriptOwnership. For example, given the following class definition: | - | ||||||||||||
180 | - | |||||||||||||
181 | \snippet code/src_script_qjsengine.cpp 7 | - | ||||||||||||
182 | - | |||||||||||||
183 | The \c staticMetaObject for the class can be exposed to JavaScript like so: | - | ||||||||||||
184 | - | |||||||||||||
185 | \snippet code/src_script_qjsengine.cpp 8 | - | ||||||||||||
186 | - | |||||||||||||
187 | Instances of the class can then be created in JavaScript: | - | ||||||||||||
188 | - | |||||||||||||
189 | \snippet code/src_script_qjsengine.cpp 9 | - | ||||||||||||
190 | - | |||||||||||||
191 | \note Currently only classes using the Q_OBJECT macro are supported; it is | - | ||||||||||||
192 | not possible to expose the \c staticMetaObject of a Q_GADGET class to | - | ||||||||||||
193 | JavaScript. | - | ||||||||||||
194 | - | |||||||||||||
195 | \section2 Dynamic QObject Properties | - | ||||||||||||
196 | - | |||||||||||||
197 | Dynamic QObject properties are not supported. For example, the following code | - | ||||||||||||
198 | will not work: | - | ||||||||||||
199 | - | |||||||||||||
200 | \snippet code/src_script_qjsengine.cpp 6 | - | ||||||||||||
201 | - | |||||||||||||
202 | \section1 Extensions | - | ||||||||||||
203 | - | |||||||||||||
204 | QJSEngine provides a compliant ECMAScript implementation. By default, | - | ||||||||||||
205 | familiar utilities like logging are not available, but they can can be | - | ||||||||||||
206 | installed via the \l installExtensions() function. | - | ||||||||||||
207 | - | |||||||||||||
208 | \sa QJSValue, {Making Applications Scriptable}, | - | ||||||||||||
209 | {List of JavaScript Objects and Functions} | - | ||||||||||||
210 | - | |||||||||||||
211 | */ | - | ||||||||||||
212 | - | |||||||||||||
213 | /*! | - | ||||||||||||
214 | \enum QJSEngine::Extension | - | ||||||||||||
215 | - | |||||||||||||
216 | This enum is used to specify extensions to be installed via | - | ||||||||||||
217 | \l installExtensions(). | - | ||||||||||||
218 | - | |||||||||||||
219 | \value TranslationExtension Indicates that translation functions (\c qsTr(), | - | ||||||||||||
220 | for example) should be installed. | - | ||||||||||||
221 | - | |||||||||||||
222 | \value ConsoleExtension Indicates that console functions (\c console.log(), | - | ||||||||||||
223 | for example) should be installed. | - | ||||||||||||
224 | - | |||||||||||||
225 | \value GarbageCollectionExtension Indicates that garbage collection | - | ||||||||||||
226 | functions (\c gc(), for example) should be installed. | - | ||||||||||||
227 | - | |||||||||||||
228 | \value AllExtensions Indicates that all extension should be installed. | - | ||||||||||||
229 | - | |||||||||||||
230 | \b TranslationExtension | - | ||||||||||||
231 | - | |||||||||||||
232 | The relation between script translation functions and C++ translation | - | ||||||||||||
233 | functions is described in the following table: | - | ||||||||||||
234 | - | |||||||||||||
235 | \table | - | ||||||||||||
236 | \header \li Script Function \li Corresponding C++ Function | - | ||||||||||||
237 | \row \li qsTr() \li QObject::tr() | - | ||||||||||||
238 | \row \li QT_TR_NOOP() \li QT_TR_NOOP() | - | ||||||||||||
239 | \row \li qsTranslate() \li QCoreApplication::translate() | - | ||||||||||||
240 | \row \li QT_TRANSLATE_NOOP() \li QT_TRANSLATE_NOOP() | - | ||||||||||||
241 | \row \li qsTrId() \li qtTrId() | - | ||||||||||||
242 | \row \li QT_TRID_NOOP() \li QT_TRID_NOOP() | - | ||||||||||||
243 | \endtable | - | ||||||||||||
244 | - | |||||||||||||
245 | This flag also adds an \c arg() function to the string prototype. | - | ||||||||||||
246 | - | |||||||||||||
247 | For more information, see the \l {Internationalization with Qt} | - | ||||||||||||
248 | documentation. | - | ||||||||||||
249 | - | |||||||||||||
250 | \b ConsoleExtension | - | ||||||||||||
251 | - | |||||||||||||
252 | The \l {Console API}{console} object implements a subset of the | - | ||||||||||||
253 | \l {https://developer.mozilla.org/en-US/docs/Web/API/Console}{Console API}, | - | ||||||||||||
254 | which provides familiar logging functions, such as \c console.log(). | - | ||||||||||||
255 | - | |||||||||||||
256 | The list of functions added is as follows: | - | ||||||||||||
257 | - | |||||||||||||
258 | \list | - | ||||||||||||
259 | \li \c console.assert() | - | ||||||||||||
260 | \li \c console.debug() | - | ||||||||||||
261 | \li \c console.exception() | - | ||||||||||||
262 | \li \c console.info() | - | ||||||||||||
263 | \li \c console.log() (equivalent to \c console.debug()) | - | ||||||||||||
264 | \li \c console.error() | - | ||||||||||||
265 | \li \c console.time() | - | ||||||||||||
266 | \li \c console.timeEnd() | - | ||||||||||||
267 | \li \c console.trace() | - | ||||||||||||
268 | \li \c console.count() | - | ||||||||||||
269 | \li \c console.warn() | - | ||||||||||||
270 | \li \c {print()} (equivalent to \c console.debug()) | - | ||||||||||||
271 | \endlist | - | ||||||||||||
272 | - | |||||||||||||
273 | For more information, see the \l {Console API} documentation. | - | ||||||||||||
274 | - | |||||||||||||
275 | \b GarbageCollectionExtension | - | ||||||||||||
276 | - | |||||||||||||
277 | The \c gc() function is equivalent to calling \l collectGarbage(). | - | ||||||||||||
278 | */ | - | ||||||||||||
279 | - | |||||||||||||
280 | QT_BEGIN_NAMESPACE | - | ||||||||||||
281 | - | |||||||||||||
282 | static void checkForApplicationInstance() | - | ||||||||||||
283 | { | - | ||||||||||||
284 | if (!QCoreApplication::instance())
| 0-10338 | ||||||||||||
285 | qFatal("QJSEngine: Must construct a QCoreApplication before a QJSEngine"); never executed: QMessageLogger(__FILE__, 285, __PRETTY_FUNCTION__).fatal("QJSEngine: Must construct a QCoreApplication before a QJSEngine"); | 0 | ||||||||||||
286 | } executed 10338 times by 151 tests: end of block Executed by:
| 10338 | ||||||||||||
287 | - | |||||||||||||
288 | /*! | - | ||||||||||||
289 | Constructs a QJSEngine object. | - | ||||||||||||
290 | - | |||||||||||||
291 | The globalObject() is initialized to have properties as described in | - | ||||||||||||
292 | \l{ECMA-262}, Section 15.1. | - | ||||||||||||
293 | */ | - | ||||||||||||
294 | QJSEngine::QJSEngine() | - | ||||||||||||
295 | : QJSEngine(nullptr) | - | ||||||||||||
296 | { | - | ||||||||||||
297 | } executed 2662 times by 8 tests: end of block Executed by:
| 2662 | ||||||||||||
298 | - | |||||||||||||
299 | /*! | - | ||||||||||||
300 | Constructs a QJSEngine object with the given \a parent. | - | ||||||||||||
301 | - | |||||||||||||
302 | The globalObject() is initialized to have properties as described in | - | ||||||||||||
303 | \l{ECMA-262}, Section 15.1. | - | ||||||||||||
304 | */ | - | ||||||||||||
305 | - | |||||||||||||
306 | QJSEngine::QJSEngine(QObject *parent) | - | ||||||||||||
307 | : QObject(*new QJSEnginePrivate, parent) | - | ||||||||||||
308 | , m_v4Engine(new QV4::ExecutionEngine(this)) | - | ||||||||||||
309 | { | - | ||||||||||||
310 | m_v4Engine->v8Engine = new QV8Engine(m_v4Engine); | - | ||||||||||||
311 | checkForApplicationInstance(); | - | ||||||||||||
312 | - | |||||||||||||
313 | QJSEnginePrivate::addToDebugServer(this); | - | ||||||||||||
314 | } executed 2664 times by 8 tests: end of block Executed by:
| 2664 | ||||||||||||
315 | - | |||||||||||||
316 | /*! | - | ||||||||||||
317 | \internal | - | ||||||||||||
318 | */ | - | ||||||||||||
319 | QJSEngine::QJSEngine(QJSEnginePrivate &dd, QObject *parent) | - | ||||||||||||
320 | : QObject(dd, parent) | - | ||||||||||||
321 | , m_v4Engine(new QV4::ExecutionEngine(this)) | - | ||||||||||||
322 | { | - | ||||||||||||
323 | m_v4Engine->v8Engine = new QV8Engine(m_v4Engine); | - | ||||||||||||
324 | checkForApplicationInstance(); | - | ||||||||||||
325 | } executed 7674 times by 148 tests: end of block Executed by:
| 7674 | ||||||||||||
326 | - | |||||||||||||
327 | /*! | - | ||||||||||||
328 | Destroys this QJSEngine. | - | ||||||||||||
329 | - | |||||||||||||
330 | Garbage is not collected from the persistent JS heap during QJSEngine | - | ||||||||||||
331 | destruction. If you need all memory freed, call collectGarbage manually | - | ||||||||||||
332 | right before destroying the QJSEngine. | - | ||||||||||||
333 | */ | - | ||||||||||||
334 | QJSEngine::~QJSEngine() | - | ||||||||||||
335 | { | - | ||||||||||||
336 | QJSEnginePrivate::removeFromDebugServer(this); | - | ||||||||||||
337 | delete m_v4Engine->v8Engine; | - | ||||||||||||
338 | delete m_v4Engine; | - | ||||||||||||
339 | } executed 10324 times by 151 tests: end of block Executed by:
| 10324 | ||||||||||||
340 | - | |||||||||||||
341 | /*! | - | ||||||||||||
342 | \fn QV4::ExecutionEngine *QJSEngine::handle() const | - | ||||||||||||
343 | \internal | - | ||||||||||||
344 | */ | - | ||||||||||||
345 | - | |||||||||||||
346 | /*! | - | ||||||||||||
347 | Runs the garbage collector. | - | ||||||||||||
348 | - | |||||||||||||
349 | The garbage collector will attempt to reclaim memory by locating and disposing of objects that are | - | ||||||||||||
350 | no longer reachable in the script environment. | - | ||||||||||||
351 | - | |||||||||||||
352 | Normally you don't need to call this function; the garbage collector will automatically be invoked | - | ||||||||||||
353 | when the QJSEngine decides that it's wise to do so (i.e. when a certain number of new objects | - | ||||||||||||
354 | have been created). However, you can call this function to explicitly request that garbage | - | ||||||||||||
355 | collection should be performed as soon as possible. | - | ||||||||||||
356 | */ | - | ||||||||||||
357 | void QJSEngine::collectGarbage() | - | ||||||||||||
358 | { | - | ||||||||||||
359 | m_v4Engine->memoryManager->runGC(); | - | ||||||||||||
360 | } executed 280 times by 11 tests: end of block Executed by:
| 280 | ||||||||||||
361 | - | |||||||||||||
362 | #if QT_DEPRECATED_SINCE(5, 6) | - | ||||||||||||
363 | - | |||||||||||||
364 | /*! | - | ||||||||||||
365 | \since 5.4 | - | ||||||||||||
366 | \obsolete | - | ||||||||||||
367 | - | |||||||||||||
368 | Installs translator functions on the given \a object, or on the Global | - | ||||||||||||
369 | Object if no object is specified. | - | ||||||||||||
370 | - | |||||||||||||
371 | The relation between script translator functions and C++ translator | - | ||||||||||||
372 | functions is described in the following table: | - | ||||||||||||
373 | - | |||||||||||||
374 | \table | - | ||||||||||||
375 | \header \li Script Function \li Corresponding C++ Function | - | ||||||||||||
376 | \row \li qsTr() \li QObject::tr() | - | ||||||||||||
377 | \row \li QT_TR_NOOP() \li QT_TR_NOOP() | - | ||||||||||||
378 | \row \li qsTranslate() \li QCoreApplication::translate() | - | ||||||||||||
379 | \row \li QT_TRANSLATE_NOOP() \li QT_TRANSLATE_NOOP() | - | ||||||||||||
380 | \row \li qsTrId() \li qtTrId() | - | ||||||||||||
381 | \row \li QT_TRID_NOOP() \li QT_TRID_NOOP() | - | ||||||||||||
382 | \endtable | - | ||||||||||||
383 | - | |||||||||||||
384 | It also adds an arg() method to the string prototype. | - | ||||||||||||
385 | - | |||||||||||||
386 | \sa {Internationalization with Qt} | - | ||||||||||||
387 | */ | - | ||||||||||||
388 | void QJSEngine::installTranslatorFunctions(const QJSValue &object) | - | ||||||||||||
389 | { | - | ||||||||||||
390 | installExtensions(TranslationExtension, object); | - | ||||||||||||
391 | } executed 142 times by 1 test: end of block Executed by:
| 142 | ||||||||||||
392 | - | |||||||||||||
393 | #endif // QT_DEPRECATED_SINCE(5, 6) | - | ||||||||||||
394 | - | |||||||||||||
395 | - | |||||||||||||
396 | /*! | - | ||||||||||||
397 | \since 5.6 | - | ||||||||||||
398 | - | |||||||||||||
399 | Installs JavaScript \a extensions to add functionality that is not | - | ||||||||||||
400 | available in a standard ECMAScript implementation. | - | ||||||||||||
401 | - | |||||||||||||
402 | The extensions are installed on the given \a object, or on the | - | ||||||||||||
403 | \l {globalObject()}{Global Object} if no object is specified. | - | ||||||||||||
404 | - | |||||||||||||
405 | Several extensions can be installed at once by \c {OR}-ing the enum values: | - | ||||||||||||
406 | - | |||||||||||||
407 | \code | - | ||||||||||||
408 | installExtensions(QJSEngine::TranslationExtension | QJSEngine::ConsoleExtension); | - | ||||||||||||
409 | \endcode | - | ||||||||||||
410 | - | |||||||||||||
411 | \sa Extension | - | ||||||||||||
412 | */ | - | ||||||||||||
413 | void QJSEngine::installExtensions(QJSEngine::Extensions extensions, const QJSValue &object) | - | ||||||||||||
414 | { | - | ||||||||||||
415 | QV4::ExecutionEngine *otherEngine = QJSValuePrivate::engine(&object); | - | ||||||||||||
416 | if (otherEngine && otherEngine != m_v4Engine) {
| 0-164 | ||||||||||||
417 | qWarning("QJSEngine: Trying to install extensions from a different engine"); | - | ||||||||||||
418 | return; never executed: return; | 0 | ||||||||||||
419 | } | - | ||||||||||||
420 | - | |||||||||||||
421 | QV4::Scope scope(m_v4Engine); | - | ||||||||||||
422 | QV4::ScopedObject obj(scope); | - | ||||||||||||
423 | QV4::Value *val = QJSValuePrivate::getValue(&object); | - | ||||||||||||
424 | if (val)
| 0-164 | ||||||||||||
425 | obj = val; never executed: obj = val; | 0 | ||||||||||||
426 | if (!obj)
| 0-164 | ||||||||||||
427 | obj = scope.engine->globalObject; executed 164 times by 1 test: obj = scope.engine->globalObject; Executed by:
| 164 | ||||||||||||
428 | - | |||||||||||||
429 | QV4::GlobalExtensions::init(obj, extensions); | - | ||||||||||||
430 | } executed 164 times by 1 test: end of block Executed by:
| 164 | ||||||||||||
431 | - | |||||||||||||
432 | /*! | - | ||||||||||||
433 | Evaluates \a program, using \a lineNumber as the base line number, | - | ||||||||||||
434 | and returns the result of the evaluation. | - | ||||||||||||
435 | - | |||||||||||||
436 | The script code will be evaluated in the context of the global object. | - | ||||||||||||
437 | - | |||||||||||||
438 | The evaluation of \a program can cause an \l{Script Exceptions}{exception} in the | - | ||||||||||||
439 | engine; in this case the return value will be the exception | - | ||||||||||||
440 | that was thrown (typically an \c{Error} object; see | - | ||||||||||||
441 | QJSValue::isError()). | - | ||||||||||||
442 | - | |||||||||||||
443 | \a lineNumber is used to specify a starting line number for \a | - | ||||||||||||
444 | program; line number information reported by the engine that pertains | - | ||||||||||||
445 | to this evaluation will be based on this argument. For example, if | - | ||||||||||||
446 | \a program consists of two lines of code, and the statement on the | - | ||||||||||||
447 | second line causes a script exception, the exception line number | - | ||||||||||||
448 | would be \a lineNumber plus one. When no starting line number is | - | ||||||||||||
449 | specified, line numbers will be 1-based. | - | ||||||||||||
450 | - | |||||||||||||
451 | \a fileName is used for error reporting. For example, in error objects | - | ||||||||||||
452 | the file name is accessible through the "fileName" property if it is | - | ||||||||||||
453 | provided with this function. | - | ||||||||||||
454 | - | |||||||||||||
455 | \note If an exception was thrown and the exception value is not an | - | ||||||||||||
456 | Error instance (i.e., QJSValue::isError() returns \c false), the | - | ||||||||||||
457 | exception value will still be returned, but there is currently no | - | ||||||||||||
458 | API for detecting that an exception did occur in this case. | - | ||||||||||||
459 | */ | - | ||||||||||||
460 | QJSValue QJSEngine::evaluate(const QString& program, const QString& fileName, int lineNumber) | - | ||||||||||||
461 | { | - | ||||||||||||
462 | QV4::ExecutionEngine *v4 = m_v4Engine; | - | ||||||||||||
463 | QV4::Scope scope(v4); | - | ||||||||||||
464 | QV4::ScopedValue result(scope); | - | ||||||||||||
465 | - | |||||||||||||
466 | QV4::Script script(v4->rootContext(), QV4::Compiler::ContextType::Global, program, fileName, lineNumber); | - | ||||||||||||
467 | script.strictMode = false; | - | ||||||||||||
468 | if (v4->currentStackFrame)
| 4-35746 | ||||||||||||
469 | script.strictMode = v4->currentStackFrame->v4Function->isStrict(); executed 4 times by 2 tests: script.strictMode = v4->currentStackFrame->v4Function->isStrict(); Executed by:
| 4 | ||||||||||||
470 | else if (v4->globalCode)
| 0-35746 | ||||||||||||
471 | script.strictMode = v4->globalCode->isStrict(); never executed: script.strictMode = v4->globalCode->isStrict(); | 0 | ||||||||||||
472 | script.inheritContext = true; | - | ||||||||||||
473 | script.parse(); | - | ||||||||||||
474 | if (!scope.engine->hasException)
| 270-35480 | ||||||||||||
475 | result = script.run(); executed 35480 times by 8 tests: result = script.run(); Executed by:
| 35480 | ||||||||||||
476 | if (scope.engine->hasException)
| 412-35338 | ||||||||||||
477 | result = v4->catchException(); executed 412 times by 5 tests: result = v4->catchException(); Executed by:
| 412 | ||||||||||||
478 | - | |||||||||||||
479 | QJSValue retval(v4, result->asReturnedValue()); | - | ||||||||||||
480 | - | |||||||||||||
481 | return retval; executed 35750 times by 8 tests: return retval; Executed by:
| 35750 | ||||||||||||
482 | } | - | ||||||||||||
483 | - | |||||||||||||
484 | /*! | - | ||||||||||||
485 | Creates a JavaScript object of class Object. | - | ||||||||||||
486 | - | |||||||||||||
487 | The prototype of the created object will be the Object | - | ||||||||||||
488 | prototype object. | - | ||||||||||||
489 | - | |||||||||||||
490 | \sa newArray(), QJSValue::setProperty() | - | ||||||||||||
491 | */ | - | ||||||||||||
492 | QJSValue QJSEngine::newObject() | - | ||||||||||||
493 | { | - | ||||||||||||
494 | QV4::Scope scope(m_v4Engine); | - | ||||||||||||
495 | QV4::ScopedValue v(scope, m_v4Engine->newObject()); | - | ||||||||||||
496 | return QJSValue(m_v4Engine, v->asReturnedValue()); executed 144 times by 6 tests: return QJSValue(m_v4Engine, v->asReturnedValue()); Executed by:
| 144 | ||||||||||||
497 | } | - | ||||||||||||
498 | - | |||||||||||||
499 | /*! | - | ||||||||||||
500 | Creates a JavaScript object of class Array with the given \a length. | - | ||||||||||||
501 | - | |||||||||||||
502 | \sa newObject() | - | ||||||||||||
503 | */ | - | ||||||||||||
504 | QJSValue QJSEngine::newArray(uint length) | - | ||||||||||||
505 | { | - | ||||||||||||
506 | QV4::Scope scope(m_v4Engine); | - | ||||||||||||
507 | QV4::ScopedArrayObject array(scope, m_v4Engine->newArrayObject()); | - | ||||||||||||
508 | if (length < 0x1000)
| 2-32 | ||||||||||||
509 | array->arrayReserve(length); executed 32 times by 7 tests: array->arrayReserve(length); Executed by:
| 32 | ||||||||||||
510 | array->setArrayLengthUnchecked(length); | - | ||||||||||||
511 | return QJSValue(m_v4Engine, array.asReturnedValue()); executed 34 times by 7 tests: return QJSValue(m_v4Engine, array.asReturnedValue()); Executed by:
| 34 | ||||||||||||
512 | } | - | ||||||||||||
513 | - | |||||||||||||
514 | /*! | - | ||||||||||||
515 | Creates a JavaScript object that wraps the given QObject \a | - | ||||||||||||
516 | object, using JavaScriptOwnership. | - | ||||||||||||
517 | - | |||||||||||||
518 | Signals and slots, properties and children of \a object are | - | ||||||||||||
519 | available as properties of the created QJSValue. | - | ||||||||||||
520 | - | |||||||||||||
521 | If \a object is a null pointer, this function returns a null value. | - | ||||||||||||
522 | - | |||||||||||||
523 | If a default prototype has been registered for the \a object's class | - | ||||||||||||
524 | (or its superclass, recursively), the prototype of the new script | - | ||||||||||||
525 | object will be set to be that default prototype. | - | ||||||||||||
526 | - | |||||||||||||
527 | If the given \a object is deleted outside of the engine's control, any | - | ||||||||||||
528 | attempt to access the deleted QObject's members through the JavaScript | - | ||||||||||||
529 | wrapper object (either by script code or C++) will result in a | - | ||||||||||||
530 | \l{Script Exceptions}{script exception}. | - | ||||||||||||
531 | - | |||||||||||||
532 | \sa QJSValue::toQObject() | - | ||||||||||||
533 | */ | - | ||||||||||||
534 | QJSValue QJSEngine::newQObject(QObject *object) | - | ||||||||||||
535 | { | - | ||||||||||||
536 | Q_D(QJSEngine); | - | ||||||||||||
537 | QV4::ExecutionEngine *v4 = m_v4Engine; | - | ||||||||||||
538 | QV4::Scope scope(v4); | - | ||||||||||||
539 | if (object) {
| 6-282 | ||||||||||||
540 | QQmlData *ddata = QQmlData::get(object, true); | - | ||||||||||||
541 | if (!ddata || !ddata->explicitIndestructibleSet)
| 0-282 | ||||||||||||
542 | QQmlEngine::setObjectOwnership(object, QQmlEngine::JavaScriptOwnership); executed 260 times by 4 tests: QQmlEngine::setObjectOwnership(object, QQmlEngine::JavaScriptOwnership); Executed by:
| 260 | ||||||||||||
543 | } executed 282 times by 5 tests: end of block Executed by:
| 282 | ||||||||||||
544 | QV4::ScopedValue v(scope, QV4::QObjectWrapper::wrap(v4, object)); | - | ||||||||||||
545 | return QJSValue(v4, v->asReturnedValue()); executed 288 times by 5 tests: return QJSValue(v4, v->asReturnedValue()); Executed by:
| 288 | ||||||||||||
546 | } | - | ||||||||||||
547 | - | |||||||||||||
548 | /*! | - | ||||||||||||
549 | \since 5.8 | - | ||||||||||||
550 | - | |||||||||||||
551 | Creates a JavaScript object that wraps the given QMetaObject | - | ||||||||||||
552 | The \a metaObject must outlive the script engine. It is recommended to only | - | ||||||||||||
553 | use this method with static metaobjects. | - | ||||||||||||
554 | - | |||||||||||||
555 | - | |||||||||||||
556 | When called as a constructor, a new instance of the class will be created. | - | ||||||||||||
557 | Only constructors exposed by Q_INVOKABLE will be visible from the script engine. | - | ||||||||||||
558 | - | |||||||||||||
559 | \sa newQObject(), {QObject Integration} | - | ||||||||||||
560 | */ | - | ||||||||||||
561 | - | |||||||||||||
562 | QJSValue QJSEngine::newQMetaObject(const QMetaObject* metaObject) { | - | ||||||||||||
563 | Q_D(QJSEngine); | - | ||||||||||||
564 | QV4::ExecutionEngine *v4 = m_v4Engine; | - | ||||||||||||
565 | QV4::Scope scope(v4); | - | ||||||||||||
566 | QV4::ScopedValue v(scope, QV4::QMetaObjectWrapper::create(v4, metaObject)); | - | ||||||||||||
567 | return QJSValue(v4, v->asReturnedValue()); executed 6 times by 1 test: return QJSValue(v4, v->asReturnedValue()); Executed by:
| 6 | ||||||||||||
568 | } | - | ||||||||||||
569 | - | |||||||||||||
570 | /*! \fn template <typename T> QJSValue QJSEngine::newQMetaObject() | - | ||||||||||||
571 | - | |||||||||||||
572 | \since 5.8 | - | ||||||||||||
573 | Creates a JavaScript object that wraps the static QMetaObject associated | - | ||||||||||||
574 | with class \c{T}. | - | ||||||||||||
575 | - | |||||||||||||
576 | \sa newQObject(), {QObject Integration} | - | ||||||||||||
577 | */ | - | ||||||||||||
578 | - | |||||||||||||
579 | - | |||||||||||||
580 | /*! | - | ||||||||||||
581 | Returns this engine's Global Object. | - | ||||||||||||
582 | - | |||||||||||||
583 | By default, the Global Object contains the built-in objects that are | - | ||||||||||||
584 | part of \l{ECMA-262}, such as Math, Date and String. Additionally, | - | ||||||||||||
585 | you can set properties of the Global Object to make your own | - | ||||||||||||
586 | extensions available to all script code. Non-local variables in | - | ||||||||||||
587 | script code will be created as properties of the Global Object, as | - | ||||||||||||
588 | well as local variables in global code. | - | ||||||||||||
589 | */ | - | ||||||||||||
590 | QJSValue QJSEngine::globalObject() const | - | ||||||||||||
591 | { | - | ||||||||||||
592 | QV4::Scope scope(m_v4Engine); | - | ||||||||||||
593 | QV4::ScopedValue v(scope, m_v4Engine->globalObject); | - | ||||||||||||
594 | return QJSValue(m_v4Engine, v->asReturnedValue()); executed 348 times by 3 tests: return QJSValue(m_v4Engine, v->asReturnedValue()); Executed by:
| 348 | ||||||||||||
595 | } | - | ||||||||||||
596 | - | |||||||||||||
597 | /*! | - | ||||||||||||
598 | * \internal | - | ||||||||||||
599 | * used by QJSEngine::toScriptValue | - | ||||||||||||
600 | */ | - | ||||||||||||
601 | QJSValue QJSEngine::create(int type, const void *ptr) | - | ||||||||||||
602 | { | - | ||||||||||||
603 | QV4::Scope scope(m_v4Engine); | - | ||||||||||||
604 | QV4::ScopedValue v(scope, scope.engine->metaTypeToJS(type, ptr)); | - | ||||||||||||
605 | return QJSValue(m_v4Engine, v->asReturnedValue()); executed 48668 times by 5 tests: return QJSValue(m_v4Engine, v->asReturnedValue()); Executed by:
| 48668 | ||||||||||||
606 | } | - | ||||||||||||
607 | - | |||||||||||||
608 | /*! | - | ||||||||||||
609 | \internal | - | ||||||||||||
610 | convert \a value to \a type, store the result in \a ptr | - | ||||||||||||
611 | */ | - | ||||||||||||
612 | bool QJSEngine::convertV2(const QJSValue &value, int type, void *ptr) | - | ||||||||||||
613 | { | - | ||||||||||||
614 | QV4::ExecutionEngine *v4 = QJSValuePrivate::engine(&value); | - | ||||||||||||
615 | QV4::Value scratch; | - | ||||||||||||
616 | QV4::Value *val = QJSValuePrivate::valueForData(&value, &scratch); | - | ||||||||||||
617 | if (v4) {
| 152-330 | ||||||||||||
618 | QV4::Scope scope(v4); | - | ||||||||||||
619 | QV4::ScopedValue v(scope, *val); | - | ||||||||||||
620 | return scope.engine->metaTypeFromJS(v, type, ptr); executed 330 times by 4 tests: return scope.engine->metaTypeFromJS(v, type, ptr); Executed by:
| 330 | ||||||||||||
621 | } | - | ||||||||||||
622 | - | |||||||||||||
623 | if (!val) {
| 44-108 | ||||||||||||
624 | QVariant *variant = QJSValuePrivate::getVariant(&value); | - | ||||||||||||
625 | Q_ASSERT(variant); | - | ||||||||||||
626 | - | |||||||||||||
627 | if (variant->userType() == QMetaType::QString) {
| 0-44 | ||||||||||||
628 | QString string = variant->toString(); | - | ||||||||||||
629 | // have a string based value without engine. Do conversion manually | - | ||||||||||||
630 | if (type == QMetaType::Bool) {
| 8-36 | ||||||||||||
631 | *reinterpret_cast<bool*>(ptr) = string.length() != 0; | - | ||||||||||||
632 | return true; executed 8 times by 1 test: return true; Executed by:
| 8 | ||||||||||||
633 | } | - | ||||||||||||
634 | if (type == QMetaType::QString) {
| 2-34 | ||||||||||||
635 | *reinterpret_cast<QString*>(ptr) = string; | - | ||||||||||||
636 | return true; executed 2 times by 1 test: return true; Executed by:
| 2 | ||||||||||||
637 | } | - | ||||||||||||
638 | double d = QV4::RuntimeHelpers::stringToNumber(string); | - | ||||||||||||
639 | switch (type) { | - | ||||||||||||
640 | case QMetaType::Int: executed 14 times by 1 test: case QMetaType::Int: Executed by:
| 14 | ||||||||||||
641 | *reinterpret_cast<int*>(ptr) = QV4::Primitive::toInt32(d); | - | ||||||||||||
642 | return true; executed 14 times by 1 test: return true; Executed by:
| 14 | ||||||||||||
643 | case QMetaType::UInt: executed 14 times by 1 test: case QMetaType::UInt: Executed by:
| 14 | ||||||||||||
644 | *reinterpret_cast<uint*>(ptr) = QV4::Primitive::toUInt32(d); | - | ||||||||||||
645 | return true; executed 14 times by 1 test: return true; Executed by:
| 14 | ||||||||||||
646 | case QMetaType::LongLong: never executed: case QMetaType::LongLong: | 0 | ||||||||||||
647 | *reinterpret_cast<qlonglong*>(ptr) = QV4::Primitive::toInteger(d); | - | ||||||||||||
648 | return true; never executed: return true; | 0 | ||||||||||||
649 | case QMetaType::ULongLong: never executed: case QMetaType::ULongLong: | 0 | ||||||||||||
650 | *reinterpret_cast<qulonglong*>(ptr) = QV4::Primitive::toInteger(d); | - | ||||||||||||
651 | return true; never executed: return true; | 0 | ||||||||||||
652 | case QMetaType::Double: executed 4 times by 1 test: case QMetaType::Double: Executed by:
| 4 | ||||||||||||
653 | *reinterpret_cast<double*>(ptr) = d; | - | ||||||||||||
654 | return true; executed 4 times by 1 test: return true; Executed by:
| 4 | ||||||||||||
655 | case QMetaType::Float: never executed: case QMetaType::Float: | 0 | ||||||||||||
656 | *reinterpret_cast<float*>(ptr) = d; | - | ||||||||||||
657 | return true; never executed: return true; | 0 | ||||||||||||
658 | case QMetaType::Short: never executed: case QMetaType::Short: | 0 | ||||||||||||
659 | *reinterpret_cast<short*>(ptr) = QV4::Primitive::toInt32(d); | - | ||||||||||||
660 | return true; never executed: return true; | 0 | ||||||||||||
661 | case QMetaType::UShort: never executed: case QMetaType::UShort: | 0 | ||||||||||||
662 | *reinterpret_cast<unsigned short*>(ptr) = QV4::Primitive::toUInt32(d); | - | ||||||||||||
663 | return true; never executed: return true; | 0 | ||||||||||||
664 | case QMetaType::Char: never executed: case QMetaType::Char: | 0 | ||||||||||||
665 | *reinterpret_cast<char*>(ptr) = QV4::Primitive::toInt32(d); | - | ||||||||||||
666 | return true; never executed: return true; | 0 | ||||||||||||
667 | case QMetaType::UChar: never executed: case QMetaType::UChar: | 0 | ||||||||||||
668 | *reinterpret_cast<unsigned char*>(ptr) = QV4::Primitive::toUInt32(d); | - | ||||||||||||
669 | return true; never executed: return true; | 0 | ||||||||||||
670 | case QMetaType::QChar: never executed: case QMetaType::QChar: | 0 | ||||||||||||
671 | *reinterpret_cast<QChar*>(ptr) = QV4::Primitive::toUInt32(d); | - | ||||||||||||
672 | return true; never executed: return true; | 0 | ||||||||||||
673 | default: executed 2 times by 1 test: default: Executed by:
| 2 | ||||||||||||
674 | return false; executed 2 times by 1 test: return false; Executed by:
| 2 | ||||||||||||
675 | } | - | ||||||||||||
676 | } else { | - | ||||||||||||
677 | return QMetaType::convert(&variant->data_ptr(), variant->userType(), ptr, type); never executed: return QMetaType::convert(&variant->data_ptr(), variant->userType(), ptr, type); | 0 | ||||||||||||
678 | } | - | ||||||||||||
679 | } | - | ||||||||||||
680 | - | |||||||||||||
681 | Q_ASSERT(val); | - | ||||||||||||
682 | - | |||||||||||||
683 | switch (type) { | - | ||||||||||||
684 | case QMetaType::Bool: executed 28 times by 1 test: case QMetaType::Bool: Executed by:
| 28 | ||||||||||||
685 | *reinterpret_cast<bool*>(ptr) = val->toBoolean(); | - | ||||||||||||
686 | return true; executed 28 times by 1 test: return true; Executed by:
| 28 | ||||||||||||
687 | case QMetaType::Int: executed 18 times by 1 test: case QMetaType::Int: Executed by:
| 18 | ||||||||||||
688 | *reinterpret_cast<int*>(ptr) = val->toInt32(); | - | ||||||||||||
689 | return true; executed 18 times by 1 test: return true; Executed by:
| 18 | ||||||||||||
690 | case QMetaType::UInt: executed 14 times by 1 test: case QMetaType::UInt: Executed by:
| 14 | ||||||||||||
691 | *reinterpret_cast<uint*>(ptr) = val->toUInt32(); | - | ||||||||||||
692 | return true; executed 14 times by 1 test: return true; Executed by:
| 14 | ||||||||||||
693 | case QMetaType::LongLong: executed 2 times by 1 test: case QMetaType::LongLong: Executed by:
| 2 | ||||||||||||
694 | *reinterpret_cast<qlonglong*>(ptr) = val->toInteger(); | - | ||||||||||||
695 | return true; executed 2 times by 1 test: return true; Executed by:
| 2 | ||||||||||||
696 | case QMetaType::ULongLong: executed 2 times by 1 test: case QMetaType::ULongLong: Executed by:
| 2 | ||||||||||||
697 | *reinterpret_cast<qulonglong*>(ptr) = val->toInteger(); | - | ||||||||||||
698 | return true; executed 2 times by 1 test: return true; Executed by:
| 2 | ||||||||||||
699 | case QMetaType::Double: executed 10 times by 2 tests: case QMetaType::Double: Executed by:
| 10 | ||||||||||||
700 | *reinterpret_cast<double*>(ptr) = val->toNumber(); | - | ||||||||||||
701 | return true; executed 10 times by 2 tests: return true; Executed by:
| 10 | ||||||||||||
702 | case QMetaType::QString: executed 6 times by 1 test: case QMetaType::QString: Executed by:
| 6 | ||||||||||||
703 | *reinterpret_cast<QString*>(ptr) = val->toQStringNoThrow(); | - | ||||||||||||
704 | return true; executed 6 times by 1 test: return true; Executed by:
| 6 | ||||||||||||
705 | case QMetaType::Float: executed 2 times by 1 test: case QMetaType::Float: Executed by:
| 2 | ||||||||||||
706 | *reinterpret_cast<float*>(ptr) = val->toNumber(); | - | ||||||||||||
707 | return true; executed 2 times by 1 test: return true; Executed by:
| 2 | ||||||||||||
708 | case QMetaType::Short: executed 2 times by 1 test: case QMetaType::Short: Executed by:
| 2 | ||||||||||||
709 | *reinterpret_cast<short*>(ptr) = val->toInt32(); | - | ||||||||||||
710 | return true; executed 2 times by 1 test: return true; Executed by:
| 2 | ||||||||||||
711 | case QMetaType::UShort: executed 2 times by 1 test: case QMetaType::UShort: Executed by:
| 2 | ||||||||||||
712 | *reinterpret_cast<unsigned short*>(ptr) = val->toUInt16(); | - | ||||||||||||
713 | return true; executed 2 times by 1 test: return true; Executed by:
| 2 | ||||||||||||
714 | case QMetaType::Char: executed 2 times by 1 test: case QMetaType::Char: Executed by:
| 2 | ||||||||||||
715 | *reinterpret_cast<char*>(ptr) = val->toInt32(); | - | ||||||||||||
716 | return true; executed 2 times by 1 test: return true; Executed by:
| 2 | ||||||||||||
717 | case QMetaType::UChar: executed 2 times by 1 test: case QMetaType::UChar: Executed by:
| 2 | ||||||||||||
718 | *reinterpret_cast<unsigned char*>(ptr) = val->toUInt16(); | - | ||||||||||||
719 | return true; executed 2 times by 1 test: return true; Executed by:
| 2 | ||||||||||||
720 | case QMetaType::QChar: never executed: case QMetaType::QChar: | 0 | ||||||||||||
721 | *reinterpret_cast<QChar*>(ptr) = val->toUInt16(); | - | ||||||||||||
722 | return true; never executed: return true; | 0 | ||||||||||||
723 | default: executed 18 times by 1 test: default: Executed by:
| 18 | ||||||||||||
724 | return false; executed 18 times by 1 test: return false; Executed by:
| 18 | ||||||||||||
725 | } | - | ||||||||||||
726 | } | - | ||||||||||||
727 | - | |||||||||||||
728 | /*! \fn template <typename T> QJSValue QJSEngine::toScriptValue(const T &value) | - | ||||||||||||
729 | - | |||||||||||||
730 | Creates a QJSValue with the given \a value. | - | ||||||||||||
731 | - | |||||||||||||
732 | \sa fromScriptValue() | - | ||||||||||||
733 | */ | - | ||||||||||||
734 | - | |||||||||||||
735 | /*! \fn template <typename T> T QJSEngine::fromScriptValue(const QJSValue &value) | - | ||||||||||||
736 | - | |||||||||||||
737 | Returns the given \a value converted to the template type \c{T}. | - | ||||||||||||
738 | - | |||||||||||||
739 | \sa toScriptValue() | - | ||||||||||||
740 | */ | - | ||||||||||||
741 | - | |||||||||||||
742 | /*! | - | ||||||||||||
743 | Throws a run-time error (exception) with the given \a message. | - | ||||||||||||
744 | - | |||||||||||||
745 | This method is the C++ counterpart of a \c throw() expression in | - | ||||||||||||
746 | JavaScript. It enables C++ code to report run-time errors to QJSEngine. | - | ||||||||||||
747 | Therefore it should only be called from C++ code that was invoked by a | - | ||||||||||||
748 | JavaScript function through QJSEngine. | - | ||||||||||||
749 | - | |||||||||||||
750 | When returning from C++, the engine will interrupt the normal flow of | - | ||||||||||||
751 | execution and call the the next pre-registered exception handler with | - | ||||||||||||
752 | an error object that contains the given \a message. The error object | - | ||||||||||||
753 | will point to the location of the top-most context on the JavaScript | - | ||||||||||||
754 | caller stack; specifically, it will have properties \c lineNumber, | - | ||||||||||||
755 | \c fileName and \c stack. These properties are described in | - | ||||||||||||
756 | \l{Script Exceptions}. | - | ||||||||||||
757 | - | |||||||||||||
758 | In the following example a C++ method in \e FileAccess.cpp throws an error | - | ||||||||||||
759 | in \e qmlFile.qml at the position where \c readFileAsText() is called: | - | ||||||||||||
760 | - | |||||||||||||
761 | \code | - | ||||||||||||
762 | // qmlFile.qml | - | ||||||||||||
763 | function someFunction() { | - | ||||||||||||
764 | ... | - | ||||||||||||
765 | var text = FileAccess.readFileAsText("/path/to/file.txt"); | - | ||||||||||||
766 | } | - | ||||||||||||
767 | \endcode | - | ||||||||||||
768 | - | |||||||||||||
769 | \code | - | ||||||||||||
770 | // FileAccess.cpp | - | ||||||||||||
771 | // Assuming that FileAccess is a QObject-derived class that has been | - | ||||||||||||
772 | // registered as a singleton type and provides an invokable method | - | ||||||||||||
773 | // readFileAsText() | - | ||||||||||||
774 | - | |||||||||||||
775 | QJSValue FileAccess::readFileAsText(const QString & filePath) { | - | ||||||||||||
776 | QFile file(filePath); | - | ||||||||||||
777 | - | |||||||||||||
778 | if (!file.open(QIODevice::ReadOnly)) { | - | ||||||||||||
779 | jsEngine->throwError(file.errorString()); | - | ||||||||||||
780 | return QString(); | - | ||||||||||||
781 | } | - | ||||||||||||
782 | - | |||||||||||||
783 | ... | - | ||||||||||||
784 | return content; | - | ||||||||||||
785 | } | - | ||||||||||||
786 | \endcode | - | ||||||||||||
787 | - | |||||||||||||
788 | It is also possible to catch the thrown error in JavaScript: | - | ||||||||||||
789 | \code | - | ||||||||||||
790 | // qmlFile.qml | - | ||||||||||||
791 | function someFunction() { | - | ||||||||||||
792 | ... | - | ||||||||||||
793 | var text; | - | ||||||||||||
794 | try { | - | ||||||||||||
795 | text = FileAccess.readFileAsText("/path/to/file.txt"); | - | ||||||||||||
796 | } catch (error) { | - | ||||||||||||
797 | console.warn("In " + error.fileName + ":" + "error.lineNumber" + | - | ||||||||||||
798 | ": " + error.message); | - | ||||||||||||
799 | } | - | ||||||||||||
800 | } | - | ||||||||||||
801 | \endcode | - | ||||||||||||
802 | - | |||||||||||||
803 | \since Qt 5.12 | - | ||||||||||||
804 | \sa {Script Exceptions} | - | ||||||||||||
805 | */ | - | ||||||||||||
806 | void QJSEngine::throwError(const QString &message) | - | ||||||||||||
807 | { | - | ||||||||||||
808 | m_v4Engine->throwError(message); | - | ||||||||||||
809 | } executed 2 times by 1 test: end of block Executed by:
| 2 | ||||||||||||
810 | - | |||||||||||||
811 | QJSEnginePrivate *QJSEnginePrivate::get(QV4::ExecutionEngine *e) | - | ||||||||||||
812 | { | - | ||||||||||||
813 | return e->jsEngine()->d_func(); executed 369004 times by 44 tests: return e->jsEngine()->d_func(); Executed by:
| 369004 | ||||||||||||
814 | } | - | ||||||||||||
815 | - | |||||||||||||
816 | QJSEnginePrivate::~QJSEnginePrivate() | - | ||||||||||||
817 | { | - | ||||||||||||
818 | QQmlMetaType::freeUnusedTypesAndCaches(); | - | ||||||||||||
819 | } executed 10324 times by 151 tests: end of block Executed by:
| 10324 | ||||||||||||
820 | - | |||||||||||||
821 | void QJSEnginePrivate::addToDebugServer(QJSEngine *q) | - | ||||||||||||
822 | { | - | ||||||||||||
823 | if (QCoreApplication::instance()->thread() != q->thread())
| 10-10328 | ||||||||||||
824 | return; executed 10 times by 2 tests: return; Executed by:
| 10 | ||||||||||||
825 | - | |||||||||||||
826 | QQmlDebugConnector *server = QQmlDebugConnector::instance(); | - | ||||||||||||
827 | if (!server || server->hasEngine(q))
| 0-10286 | ||||||||||||
828 | return; executed 10286 times by 145 tests: return; Executed by:
| 10286 | ||||||||||||
829 | - | |||||||||||||
830 | server->open(); | - | ||||||||||||
831 | server->addEngine(q); | - | ||||||||||||
832 | } executed 42 times by 7 tests: end of block Executed by:
| 42 | ||||||||||||
833 | - | |||||||||||||
834 | void QJSEnginePrivate::removeFromDebugServer(QJSEngine *q) | - | ||||||||||||
835 | { | - | ||||||||||||
836 | QQmlDebugConnector *server = QQmlDebugConnector::instance(); | - | ||||||||||||
837 | if (server && server->hasEngine(q))
| 42-18038 | ||||||||||||
838 | server->removeEngine(q); executed 42 times by 7 tests: server->removeEngine(q); Executed by:
| 42 | ||||||||||||
839 | } executed 18132 times by 151 tests: end of block Executed by:
| 18132 | ||||||||||||
840 | - | |||||||||||||
841 | /*! | - | ||||||||||||
842 | \since 5.5 | - | ||||||||||||
843 | \relates QJSEngine | - | ||||||||||||
844 | - | |||||||||||||
845 | Returns the QJSEngine associated with \a object, if any. | - | ||||||||||||
846 | - | |||||||||||||
847 | This function is useful if you have exposed a QObject to the JavaScript environment | - | ||||||||||||
848 | and later in your program would like to regain access. It does not require you to | - | ||||||||||||
849 | keep the wrapper around that was returned from QJSEngine::newQObject(). | - | ||||||||||||
850 | */ | - | ||||||||||||
851 | QJSEngine *qjsEngine(const QObject *object) | - | ||||||||||||
852 | { | - | ||||||||||||
853 | QQmlData *data = QQmlData::get(object, false); | - | ||||||||||||
854 | if (!data || data->jsWrapper.isNullOrUndefined())
| 2-16 | ||||||||||||
855 | return nullptr; executed 4 times by 1 test: return nullptr; Executed by:
| 4 | ||||||||||||
856 | return data->jsWrapper.engine()->jsEngine(); executed 14 times by 3 tests: return data->jsWrapper.engine()->jsEngine(); Executed by:
| 14 | ||||||||||||
857 | } | - | ||||||||||||
858 | - | |||||||||||||
859 | QT_END_NAMESPACE | - | ||||||||||||
860 | - | |||||||||||||
861 | #include "moc_qjsengine.cpp" | - | ||||||||||||
Source code | Switch to Preprocessed file |