aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/qml/qml/qqmlboundsignal.cpp97
-rw-r--r--src/qml/qml/qqmlboundsignal_p.h40
2 files changed, 96 insertions, 41 deletions
diff --git a/src/qml/qml/qqmlboundsignal.cpp b/src/qml/qml/qqmlboundsignal.cpp
index e5a0df8c32..8c3e1c7384 100644
--- a/src/qml/qml/qqmlboundsignal.cpp
+++ b/src/qml/qml/qqmlboundsignal.cpp
@@ -66,36 +66,44 @@ static QQmlJavaScriptExpression::VTable QQmlBoundSignalExpression_jsvtable = {
QQmlBoundSignalExpression::expressionChanged
};
+QQmlBoundSignalExpression::ExtraData::ExtraData(const QString &handlerName, const QString &parameterString,
+ const QString &expression, const QString &fileName,
+ quint16 line, quint16 column)
+ : m_handlerName(handlerName),
+ m_parameterString(parameterString),
+ m_expression(expression),
+ m_fileName(fileName),
+ m_line(line),
+ m_column(column)
+{
+}
+
QQmlBoundSignalExpression::QQmlBoundSignalExpression(QObject *target, int index,
QQmlContextData *ctxt, QObject *scope, const QString &expression,
const QString &fileName, quint16 line, quint16 column,
const QString &handlerName,
const QString &parameterString)
: QQmlJavaScriptExpression(&QQmlBoundSignalExpression_jsvtable),
- m_fileName(fileName),
- m_line(line),
- m_column(column),
m_target(target),
m_index(index),
- m_expressionFunctionValid(false),
- m_invalidParameterName(false)
+ m_extra(new ExtraData(handlerName, parameterString, expression, fileName, line, column))
{
+ setExpressionFunctionValid(false);
+ setInvalidParameterName(false);
+
init(ctxt, scope);
- m_handlerName = handlerName;
- m_parameterString = parameterString;
- m_expression = expression;
}
QQmlBoundSignalExpression::QQmlBoundSignalExpression(QObject *target, int index, QQmlContextData *ctxt, QObject *scope, const QV4::ValueRef &function)
: QQmlJavaScriptExpression(&QQmlBoundSignalExpression_jsvtable),
m_v8function(function),
- m_line(USHRT_MAX),
- m_column(USHRT_MAX),
m_target(target),
m_index(index),
- m_expressionFunctionValid(true),
- m_invalidParameterName(false)
+ m_extra(0)
{
+ setExpressionFunctionValid(true);
+ setInvalidParameterName(false);
+
init(ctxt, scope);
}
@@ -124,21 +132,55 @@ void QQmlBoundSignalExpression::expressionChanged(QQmlJavaScriptExpression *)
// bound signals do not notify on change.
}
+QString QQmlBoundSignalExpression::sourceFile() const
+{
+ if (expressionFunctionValid()) {
+ QV4::Function *f = function();
+ Q_ASSERT(f);
+ return f->sourceFile();
+ }
+ Q_ASSERT(!m_extra.isNull());
+ return m_extra->m_fileName;
+}
+
+quint16 QQmlBoundSignalExpression::lineNumber() const
+{
+ if (expressionFunctionValid()) {
+ QV4::Function *f = function();
+ Q_ASSERT(f);
+ return f->compiledFunction->location.line;
+ }
+ Q_ASSERT(!m_extra.isNull());
+ return m_extra->m_line;
+}
+
+quint16 QQmlBoundSignalExpression::columnNumber() const
+{
+ if (expressionFunctionValid()) {
+ QV4::Function *f = function();
+ Q_ASSERT(f);
+ return f->compiledFunction->location.column;
+ }
+ Q_ASSERT(!m_extra.isNull());
+ return m_extra->m_column;
+}
+
QString QQmlBoundSignalExpression::expression() const
{
- if (m_expressionFunctionValid) {
+ if (expressionFunctionValid()) {
Q_ASSERT (context() && engine());
QV4::Scope scope(QQmlEnginePrivate::get(engine())->v4engine());
QV4::ScopedValue v(scope, m_v8function.value());
return v->toQStringNoThrow();
} else {
- return m_expression;
+ Q_ASSERT(!m_extra.isNull());
+ return m_extra->m_expression;
}
}
QV4::Function *QQmlBoundSignalExpression::function() const
{
- if (m_expressionFunctionValid) {
+ if (expressionFunctionValid()) {
Q_ASSERT (context() && engine());
QV4::Scope scope(QQmlEnginePrivate::get(engine())->v4engine());
QV4::Scoped<QV4::FunctionObject> v(scope, m_v8function.value());
@@ -153,7 +195,7 @@ void QQmlBoundSignalExpression::evaluate(void **a)
{
Q_ASSERT (context() && engine());
- if (m_invalidParameterName)
+ if (invalidParameterName())
return;
QQmlEnginePrivate *ep = QQmlEnginePrivate::get(engine());
@@ -161,14 +203,15 @@ void QQmlBoundSignalExpression::evaluate(void **a)
ep->referenceScarceResources(); // "hold" scarce resources in memory during evaluation.
{
- if (!m_expressionFunctionValid) {
+ if (!expressionFunctionValid()) {
+ Q_ASSERT(!m_extra.isNull());
QString expression;
expression = QStringLiteral("(function ");
- expression += m_handlerName;
+ expression += m_extra->m_handlerName;
expression += QLatin1Char('(');
- if (m_parameterString.isEmpty()) {
+ if (m_extra->m_parameterString.isEmpty()) {
QString error;
//TODO: look at using the property cache here (as in the compiler)
// for further optimization
@@ -177,30 +220,30 @@ void QQmlBoundSignalExpression::evaluate(void **a)
if (!error.isEmpty()) {
qmlInfo(scopeObject()) << error;
- m_invalidParameterName = true;
+ setInvalidParameterName(true);
ep->dereferenceScarceResources();
return;
}
} else
- expression += m_parameterString;
+ expression += m_extra->m_parameterString;
expression += QStringLiteral(") { ");
- expression += m_expression;
+ expression += m_extra->m_expression;
expression += QStringLiteral(" })");
- m_expression.clear();
- m_handlerName.clear();
- m_parameterString.clear();
+ m_extra->m_expression.clear();
+ m_extra->m_handlerName.clear();
+ m_extra->m_parameterString.clear();
m_v8function = evalFunction(context(), scopeObject(), expression,
- m_fileName, m_line, &m_v8qmlscope);
+ m_extra->m_fileName, m_extra->m_line, &m_v8qmlscope);
if (m_v8function.isNullOrUndefined()) {
ep->dereferenceScarceResources();
return; // could not evaluate function. Not valid.
}
- m_expressionFunctionValid = true;
+ setExpressionFunctionValid(true);
}
QV8Engine *engine = ep->v8engine();
diff --git a/src/qml/qml/qqmlboundsignal_p.h b/src/qml/qml/qqmlboundsignal_p.h
index fe0dbd380e..93cff745e2 100644
--- a/src/qml/qml/qqmlboundsignal_p.h
+++ b/src/qml/qml/qqmlboundsignal_p.h
@@ -86,9 +86,9 @@ public:
// evaluation of a bound signal expression doesn't return any value
void evaluate(void **a);
- QString sourceFile() const { return m_fileName; }
- quint16 lineNumber() const { return m_line; }
- quint16 columnNumber() const { return m_column; }
+ QString sourceFile() const;
+ quint16 lineNumber() const;
+ quint16 columnNumber() const;
QString expression() const;
QV4::Function *function() const;
QObject *target() const { return m_target; }
@@ -100,23 +100,35 @@ private:
void init(QQmlContextData *ctxt, QObject *scope);
+ bool expressionFunctionValid() const { return m_extra.flag(); }
+ void setExpressionFunctionValid(bool v) { m_extra.setFlagValue(v); }
+
+ bool invalidParameterName() const { return m_extra.flag2(); }
+ void setInvalidParameterName(bool v) { m_extra.setFlag2Value(v); }
+
QV4::PersistentValue m_v8qmlscope;
QV4::PersistentValue m_v8function;
- QString m_handlerName;
- QString m_parameterString;
- //once m_v8function is valid, we clear expression and
- //extract it from m_v8function if needed.
- QString m_expression; //only used when expression needs to be rewritten
- QString m_fileName;
- quint16 m_line;
- quint16 m_column;
-
QObject *m_target;
int m_index;
- bool m_expressionFunctionValid:1;
- bool m_invalidParameterName:1;
+ // only needed when !expressionFunctionValid()
+ struct ExtraData {
+ ExtraData(const QString &handlerName, const QString &parameterString,
+ const QString &expression, const QString &fileName,
+ quint16 line, quint16 column);
+ QString m_handlerName;
+ QString m_parameterString;
+ QString m_expression;
+ QString m_fileName;
+ quint16 m_line;
+ quint16 m_column;
+ };
+
+ // We store some flag bits in the following flag pointers.
+ // flag - expressionFunctionValid
+ // flag2 - invalidParameterName
+ QFlagPointer<ExtraData> m_extra;
};
class Q_QML_PRIVATE_EXPORT QQmlAbstractBoundSignal