diff options
-rw-r--r-- | src/qml/compiler/qqmlcodegenerator.cpp | 8 | ||||
-rw-r--r-- | src/qml/qml/qqmllocale.cpp | 77 | ||||
-rw-r--r-- | src/qml/qml/qqmllocale_p.h | 58 | ||||
-rw-r--r-- | src/qml/qml/qqmlobjectcreator.cpp | 106 | ||||
-rw-r--r-- | src/qml/qml/qqmlobjectcreator_p.h | 7 | ||||
-rw-r--r-- | src/qml/qml/v8/qv8engine.cpp | 5 | ||||
-rw-r--r-- | src/quick/scenegraph/coreapi/qsgbatchrenderer.cpp | 4 | ||||
-rw-r--r-- | src/quick/scenegraph/coreapi/qsggeometry.cpp | 10 | ||||
-rw-r--r-- | tests/auto/qml/qqmllocale/tst_qqmllocale.cpp | 36 |
9 files changed, 185 insertions, 126 deletions
diff --git a/src/qml/compiler/qqmlcodegenerator.cpp b/src/qml/compiler/qqmlcodegenerator.cpp index f0dfc9b7ea..d1504b5baa 100644 --- a/src/qml/compiler/qqmlcodegenerator.cpp +++ b/src/qml/compiler/qqmlcodegenerator.cpp @@ -1664,10 +1664,6 @@ bool SignalHandlerConverter::convertSignalHandlerExpressionsToFunctionDeclaratio if (!QQmlCodeGenerator::isSignalPropertyName(propertyName)) continue; - if (binding->type != QV4::CompiledData::Binding::Type_Script) { - COMPILE_EXCEPTION(binding->location, tr("Incorrectly specified signal assignment")); - } - PropertyResolver resolver(propertyCache); Q_ASSERT(propertyName.startsWith(QStringLiteral("on"))); @@ -1736,6 +1732,10 @@ bool SignalHandlerConverter::convertSignalHandlerExpressionsToFunctionDeclaratio parameters = entry.value(); } + if (binding->type != QV4::CompiledData::Binding::Type_Script) { + COMPILE_EXCEPTION(binding->location, tr("Incorrectly specified signal assignment")); + } + QQmlJS::Engine &jsEngine = parsedQML->jsParserEngine; QQmlJS::MemoryPool *pool = jsEngine.pool(); diff --git a/src/qml/qml/qqmllocale.cpp b/src/qml/qml/qqmllocale.cpp index 75a366a7af..625b3a3175 100644 --- a/src/qml/qml/qqmllocale.cpp +++ b/src/qml/qml/qqmllocale.cpp @@ -54,62 +54,6 @@ QT_BEGIN_NAMESPACE -class QQmlLocaleData : public QV4::Object -{ - Q_MANAGED -public: - QQmlLocaleData(QV4::ExecutionEngine *engine) - : QV4::Object(engine) - { - setVTable(&static_vtbl); - } - - QLocale locale; - - static QLocale *getThisLocale(QV4::CallContext *ctx) { - QQmlLocaleData *thisObject = ctx->callData->thisObject.asObject()->as<QQmlLocaleData>(); - if (!thisObject) { - ctx->throwTypeError(); - return 0; - } - return &thisObject->locale; - } - - static QV4::ReturnedValue method_currencySymbol(QV4::CallContext *ctx); - static QV4::ReturnedValue method_dateTimeFormat(QV4::CallContext *ctx); - static QV4::ReturnedValue method_timeFormat(QV4::CallContext *ctx); - static QV4::ReturnedValue method_dateFormat(QV4::CallContext *ctx); - static QV4::ReturnedValue method_monthName(QV4::CallContext *ctx); - static QV4::ReturnedValue method_standaloneMonthName(QV4::CallContext *ctx); - static QV4::ReturnedValue method_dayName(QV4::CallContext *ctx); - static QV4::ReturnedValue method_standaloneDayName(QV4::CallContext *ctx); - - static QV4::ReturnedValue method_get_firstDayOfWeek(QV4::CallContext *ctx); - static QV4::ReturnedValue method_get_measurementSystem(QV4::CallContext *ctx); - static QV4::ReturnedValue method_get_textDirection(QV4::CallContext *ctx); - static QV4::ReturnedValue method_get_weekDays(QV4::CallContext *ctx); - static QV4::ReturnedValue method_get_uiLanguages(QV4::CallContext *ctx); - - static QV4::ReturnedValue method_get_name(QV4::CallContext *ctx); - static QV4::ReturnedValue method_get_nativeLanguageName(QV4::CallContext *ctx); - static QV4::ReturnedValue method_get_nativeCountryName(QV4::CallContext *ctx); - static QV4::ReturnedValue method_get_decimalPoint(QV4::CallContext *ctx); - static QV4::ReturnedValue method_get_groupSeparator(QV4::CallContext *ctx); - static QV4::ReturnedValue method_get_percent(QV4::CallContext *ctx); - static QV4::ReturnedValue method_get_zeroDigit(QV4::CallContext *ctx); - static QV4::ReturnedValue method_get_negativeSign(QV4::CallContext *ctx); - static QV4::ReturnedValue method_get_positiveSign(QV4::CallContext *ctx); - static QV4::ReturnedValue method_get_exponential(QV4::CallContext *ctx); - static QV4::ReturnedValue method_get_amText(QV4::CallContext *ctx); - static QV4::ReturnedValue method_get_pmText(QV4::CallContext *ctx); - -private: - static void destroy(Managed *that) - { - static_cast<QQmlLocaleData *>(that)->~QQmlLocaleData(); - } -}; - DEFINE_MANAGED_VTABLE(QQmlLocaleData); #define GET_LOCALE_DATA_RESOURCE(OBJECT) \ @@ -857,14 +801,21 @@ QQmlLocale::~QQmlLocale() { } -QV4::ReturnedValue QQmlLocale::locale(QV8Engine *v8engine, const QString &locale) +QV4::ReturnedValue QQmlLocale::locale(QV8Engine *v8engine, const QString &localeName) +{ + QLocale qlocale; + if (!localeName.isEmpty()) + qlocale = localeName; + return wrap(v8engine, qlocale); +} + +QV4::ReturnedValue QQmlLocale::wrap(QV8Engine *engine, const QLocale &locale) { - QV8LocaleDataDeletable *d = localeV8Data(v8engine); - QV4::ExecutionEngine *engine = QV8Engine::getV4(v8engine); - QV4::Scope scope(engine); - QV4::Scoped<QQmlLocaleData> wrapper(scope, new (engine->memoryManager) QQmlLocaleData(engine)); - if (!locale.isEmpty()) - wrapper->locale = QLocale(locale); + QV8LocaleDataDeletable *d = localeV8Data(engine); + QV4::ExecutionEngine *v4 = QV8Engine::getV4(engine); + QV4::Scope scope(v4); + QV4::Scoped<QQmlLocaleData> wrapper(scope, new (v4->memoryManager) QQmlLocaleData(v4)); + wrapper->locale = locale; QV4::ScopedObject p(scope, d->prototype.value()); wrapper->setPrototype(p.getPointer()); return wrapper.asReturnedValue(); diff --git a/src/qml/qml/qqmllocale_p.h b/src/qml/qml/qqmllocale_p.h index 8ca67a8c83..1f26f1834f 100644 --- a/src/qml/qml/qqmllocale_p.h +++ b/src/qml/qml/qqmllocale_p.h @@ -118,7 +118,8 @@ public: Saturday = Qt::Saturday }; - static QV4::ReturnedValue locale(QV8Engine *v8engine, const QString &lang); + static QV4::ReturnedValue locale(QV8Engine *v8engine, const QString &localeName); + static QV4::ReturnedValue wrap(QV8Engine *engine, const QLocale &locale); static void registerStringLocaleCompare(QV4::ExecutionEngine *engine); @@ -128,6 +129,61 @@ private: static QV4::ReturnedValue method_localeCompare(QV4::CallContext *ctx); }; +class QQmlLocaleData : public QV4::Object +{ + Q_MANAGED +public: + QQmlLocaleData(QV4::ExecutionEngine *engine) + : QV4::Object(engine) + { + setVTable(&static_vtbl); + } + + QLocale locale; + + static QLocale *getThisLocale(QV4::CallContext *ctx) { + QQmlLocaleData *thisObject = ctx->callData->thisObject.asObject()->as<QQmlLocaleData>(); + if (!thisObject) { + ctx->throwTypeError(); + return 0; + } + return &thisObject->locale; + } + + static QV4::ReturnedValue method_currencySymbol(QV4::CallContext *ctx); + static QV4::ReturnedValue method_dateTimeFormat(QV4::CallContext *ctx); + static QV4::ReturnedValue method_timeFormat(QV4::CallContext *ctx); + static QV4::ReturnedValue method_dateFormat(QV4::CallContext *ctx); + static QV4::ReturnedValue method_monthName(QV4::CallContext *ctx); + static QV4::ReturnedValue method_standaloneMonthName(QV4::CallContext *ctx); + static QV4::ReturnedValue method_dayName(QV4::CallContext *ctx); + static QV4::ReturnedValue method_standaloneDayName(QV4::CallContext *ctx); + + static QV4::ReturnedValue method_get_firstDayOfWeek(QV4::CallContext *ctx); + static QV4::ReturnedValue method_get_measurementSystem(QV4::CallContext *ctx); + static QV4::ReturnedValue method_get_textDirection(QV4::CallContext *ctx); + static QV4::ReturnedValue method_get_weekDays(QV4::CallContext *ctx); + static QV4::ReturnedValue method_get_uiLanguages(QV4::CallContext *ctx); + + static QV4::ReturnedValue method_get_name(QV4::CallContext *ctx); + static QV4::ReturnedValue method_get_nativeLanguageName(QV4::CallContext *ctx); + static QV4::ReturnedValue method_get_nativeCountryName(QV4::CallContext *ctx); + static QV4::ReturnedValue method_get_decimalPoint(QV4::CallContext *ctx); + static QV4::ReturnedValue method_get_groupSeparator(QV4::CallContext *ctx); + static QV4::ReturnedValue method_get_percent(QV4::CallContext *ctx); + static QV4::ReturnedValue method_get_zeroDigit(QV4::CallContext *ctx); + static QV4::ReturnedValue method_get_negativeSign(QV4::CallContext *ctx); + static QV4::ReturnedValue method_get_positiveSign(QV4::CallContext *ctx); + static QV4::ReturnedValue method_get_exponential(QV4::CallContext *ctx); + static QV4::ReturnedValue method_get_amText(QV4::CallContext *ctx); + static QV4::ReturnedValue method_get_pmText(QV4::CallContext *ctx); + +private: + static void destroy(Managed *that) + { + static_cast<QQmlLocaleData *>(that)->~QQmlLocaleData(); + } +}; QT_END_NAMESPACE diff --git a/src/qml/qml/qqmlobjectcreator.cpp b/src/qml/qml/qqmlobjectcreator.cpp index 5eeee96d14..e880289d9d 100644 --- a/src/qml/qml/qqmlobjectcreator.cpp +++ b/src/qml/qml/qqmlobjectcreator.cpp @@ -91,7 +91,7 @@ QmlObjectCreator::QmlObjectCreator(QQmlContextData *parentContext, QQmlCompiledD , compiledData(compiledData) , rootContext(0) , _qobject(0) - , _qobjectForBindings(0) + , _scopeObject(0) , _valueTypeProperty(0) , _compiledObject(0) , _ddata(0) @@ -181,7 +181,13 @@ void QmlObjectCreator::setPropertyValue(QQmlPropertyData *property, const QV4::C QV4::ExecutionEngine *v4 = QV8Engine::getV4(engine); QV4::Scope scope(v4); - // ### enums + + // ### This should be resolved earlier at compile time and the binding value should be changed accordingly. + if (property->isEnum()) { + QVariant value = binding->valueAsString(&qmlUnit->header); + QQmlPropertyPrivate::write(_qobject, *property, value, context); + return; + } switch (property->propType) { case QMetaType::QVariant: { @@ -638,7 +644,7 @@ bool QmlObjectCreator::setPropertyValue(QQmlPropertyData *property, int bindingI const int id = attachedType->attachedPropertiesId(); QObject *qmlObject = qmlAttachedPropertiesObjectById(id, _qobject); QQmlRefPointer<QQmlPropertyCache> cache = QQmlEnginePrivate::get(engine)->cache(qmlObject); - if (!populateInstance(binding->value.objectIndex, qmlObject, cache, _qobject, /*value type property*/0)) + if (!populateInstance(binding->value.objectIndex, qmlObject, cache, qmlObject, /*value type property*/0)) return false; return true; } @@ -658,11 +664,11 @@ bool QmlObjectCreator::setPropertyValue(QQmlPropertyData *property, int bindingI if (stringAt(obj->inheritedTypeNameIndex).isEmpty()) { QQmlEnginePrivate *enginePrivate = QQmlEnginePrivate::get(engine); - QQmlRefPointer<QQmlPropertyCache> groupedObjCache; - QObject *groupedObjInstance = 0; - QObject *objForBindings = _qobjectForBindings; + QQmlRefPointer<QQmlPropertyCache> groupObjectPropertyCache; + QObject *groupObject = 0; QQmlValueType *valueType = 0; QQmlPropertyData *valueTypeProperty = 0; + QObject *bindingTarget = _bindingTarget; if (QQmlValueTypeFactory::isValueType(property->propType)) { valueType = QQmlValueTypeFactory::valueType(property->propType); @@ -673,27 +679,27 @@ bool QmlObjectCreator::setPropertyValue(QQmlPropertyData *property, int bindingI valueType->read(_qobject, property->coreIndex); - groupedObjCache = enginePrivate->cache(valueType); - groupedObjInstance = valueType; + groupObjectPropertyCache = enginePrivate->cache(valueType); + groupObject = valueType; valueTypeProperty = property; } else { - groupedObjCache = enginePrivate->propertyCacheForType(property->propType); - if (!groupedObjCache) { + groupObjectPropertyCache = enginePrivate->propertyCacheForType(property->propType); + if (!groupObjectPropertyCache) { recordError(binding->location, tr("Invalid grouped property access")); return false; } - void *argv[1] = { &groupedObjInstance }; + void *argv[1] = { &groupObject }; QMetaObject::metacall(_qobject, QMetaObject::ReadProperty, property->coreIndex, argv); - if (!groupedObjInstance) { + if (!groupObject) { recordError(binding->location, tr("Cannot set properties on %1 as it is null").arg(stringAt(binding->propertyNameIndex))); return false; } - objForBindings = groupedObjInstance; + bindingTarget = groupObject; } - if (!populateInstance(binding->value.objectIndex, groupedObjInstance, groupedObjCache, objForBindings, valueTypeProperty)) + if (!populateInstance(binding->value.objectIndex, groupObject, groupObjectPropertyCache, bindingTarget, valueTypeProperty)) return false; if (valueType) @@ -703,8 +709,8 @@ bool QmlObjectCreator::setPropertyValue(QQmlPropertyData *property, int bindingI } } - if (_ddata->hasBindingBit(property->coreIndex)) - removeBindingOnProperty(_qobject, property->coreIndex); + if (_ddata->hasBindingBit(property->coreIndex) && !(binding->flags & QV4::CompiledData::Binding::IsSignalHandlerExpression)) + removeBindingOnProperty(_bindingTarget, property->coreIndex); if (binding->type == QV4::CompiledData::Binding::Type_Script) { QV4::Function *runtimeFunction = jsUnit->runtimeFunctions[binding->value.compiledScriptIndex]; @@ -714,14 +720,14 @@ bool QmlObjectCreator::setPropertyValue(QQmlPropertyData *property, int bindingI if (binding->flags & QV4::CompiledData::Binding::IsSignalHandlerExpression) { int signalIndex = _propertyCache->methodIndexToSignalIndex(property->coreIndex); - QQmlBoundSignal *bs = new QQmlBoundSignal(_qobject, signalIndex, _qobject, engine); - QQmlBoundSignalExpression *expr = new QQmlBoundSignalExpression(_qobject, signalIndex, - context, _qobject, function); + QQmlBoundSignal *bs = new QQmlBoundSignal(_bindingTarget, signalIndex, _scopeObject, engine); + QQmlBoundSignalExpression *expr = new QQmlBoundSignalExpression(_bindingTarget, signalIndex, + context, _scopeObject, function); bs->takeExpression(expr); } else { - QQmlBinding *qmlBinding = new QQmlBinding(function, _qobject, context, - QString(), 0, 0); // ### + QQmlBinding *qmlBinding = new QQmlBinding(function, _scopeObject, context, + context->urlString, binding->location.line, binding->location.column); // When writing bindings to grouped properties implemented as value types, // such as point.x: { someExpression; }, then the binding is installed on @@ -732,7 +738,7 @@ bool QmlObjectCreator::setPropertyValue(QQmlPropertyData *property, int bindingI if (_valueTypeProperty) targetCorePropertyData = QQmlPropertyPrivate::saveValueType(*_valueTypeProperty, _qobject->metaObject(), property->coreIndex, engine); - qmlBinding->setTarget(_qobjectForBindings, targetCorePropertyData, context); + qmlBinding->setTarget(_bindingTarget, targetCorePropertyData, context); qmlBinding->addToObject(); _createdBindings[bindingIndex] = qmlBinding; @@ -826,7 +832,6 @@ void QmlObjectCreator::setupFunctions() { QV4::Scope scope(_qmlContext); QV4::ScopedValue function(scope); - QQmlVMEMetaObject *vme = QQmlVMEMetaObject::get(_qobject); const quint32 *functionIdx = _compiledObject->functionOffsetTable(); for (quint32 i = 0; i < _compiledObject->nFunctions; ++i, ++functionIdx) { @@ -838,7 +843,7 @@ void QmlObjectCreator::setupFunctions() continue; function = QV4::FunctionObject::creatScriptFunction(_qmlContext, runtimeFunction); - vme->setVmeMethod(property->coreIndex, function); + _vmeMetaObject->setVmeMethod(property->coreIndex, function); } } @@ -935,15 +940,29 @@ QObject *QmlObjectCreator::createInstance(int index, QObject *parent) customParser->setCustomData(instance, data); } - if (!isComponent) { - QQmlRefPointer<QQmlPropertyCache> cache = propertyCaches.value(index); - Q_ASSERT(!cache.isNull()); + if (isComponent) + return instance; - if (!populateInstance(index, instance, cache, instance, /*value type property*/0)) - return 0; - } + QQmlRefPointer<QQmlPropertyCache> cache = propertyCaches.value(index); + Q_ASSERT(!cache.isNull()); - return instance; + QObject *scopeObject = instance; + qSwap(_scopeObject, scopeObject); + + QV4::ExecutionEngine *v4 = QV8Engine::getV4(engine); + QV4::Scope valueScope(v4); + QV4::ScopedObject jsScopeObject(valueScope, QV4::QmlContextWrapper::qmlScope(QV8Engine::get(engine), context, _scopeObject)); + QV4::Scoped<QV4::QmlBindingWrapper> qmlBindingWrapper(valueScope, new (v4->memoryManager) QV4::QmlBindingWrapper(v4->rootContext, jsScopeObject)); + QV4::ExecutionContext *qmlContext = qmlBindingWrapper->context(); + + qSwap(_qmlContext, qmlContext); + + bool result = populateInstance(index, instance, cache, /*binding target*/instance, /*value type property*/0); + + qSwap(_qmlContext, qmlContext); + qSwap(_scopeObject, scopeObject); + + return result ? instance : 0; } QQmlContextData *QmlObjectCreator::finalize() @@ -1015,33 +1034,30 @@ QQmlContextData *QmlObjectCreator::finalize() return rootContext; } -bool QmlObjectCreator::populateInstance(int index, QObject *instance, QQmlRefPointer<QQmlPropertyCache> cache, - QObject *scopeObjectForBindings, QQmlPropertyData *valueTypeProperty) +bool QmlObjectCreator::populateInstance(int index, QObject *instance, QQmlRefPointer<QQmlPropertyCache> cache, QObject *bindingTarget, QQmlPropertyData *valueTypeProperty) { const QV4::CompiledData::Object *obj = qmlUnit->objectAt(index); - Q_ASSERT(scopeObjectForBindings); - QQmlData *declarativeData = QQmlData::get(instance, /*create*/true); qSwap(_propertyCache, cache); qSwap(_qobject, instance); - qSwap(_qobjectForBindings, scopeObjectForBindings); qSwap(_valueTypeProperty, valueTypeProperty); qSwap(_compiledObject, obj); qSwap(_ddata, declarativeData); + qSwap(_bindingTarget, bindingTarget); QQmlVMEMetaObject *vmeMetaObject = 0; const QByteArray data = vmeMetaObjectData.value(index); if (!data.isEmpty()) { // install on _object - vmeMetaObject = new QQmlVMEMetaObject(_qobjectForBindings, _propertyCache, reinterpret_cast<const QQmlVMEMetaData*>(data.constData())); + vmeMetaObject = new QQmlVMEMetaObject(_qobject, _propertyCache, reinterpret_cast<const QQmlVMEMetaData*>(data.constData())); if (_ddata->propertyCache) _ddata->propertyCache->release(); _ddata->propertyCache = _propertyCache; _ddata->propertyCache->addref(); } else { - vmeMetaObject = QQmlVMEMetaObject::get(_qobjectForBindings); + vmeMetaObject = QQmlVMEMetaObject::get(_qobject); } _ddata->lineNumber = _compiledObject->location.line; @@ -1052,29 +1068,19 @@ bool QmlObjectCreator::populateInstance(int index, QObject *instance, QQmlRefPoi QVector<QQmlAbstractBinding*> createdBindings(_compiledObject->nBindings, 0); qSwap(_createdBindings, createdBindings); - QV4::ExecutionEngine *v4 = QV8Engine::getV4(engine); - QV4::Scope valueScope(v4); - QV4::ScopedObject scopeObject(valueScope, QV4::QmlContextWrapper::qmlScope(QV8Engine::get(engine), context, _qobjectForBindings)); - QV4::Scoped<QV4::QmlBindingWrapper> qmlBindingWrapper(valueScope, new (v4->memoryManager) QV4::QmlBindingWrapper(v4->rootContext, scopeObject)); - QV4::ExecutionContext *qmlContext = qmlBindingWrapper->context(); - - qSwap(_qmlContext, qmlContext); - setupBindings(); setupFunctions(); allCreatedBindings.append(_createdBindings); - qSwap(_qmlContext, qmlContext); - qSwap(_createdBindings, createdBindings); qSwap(_vmeMetaObject, vmeMetaObject); - qSwap(_propertyCache, cache); + qSwap(_bindingTarget, bindingTarget); qSwap(_ddata, declarativeData); qSwap(_compiledObject, obj); qSwap(_valueTypeProperty, valueTypeProperty); - qSwap(_qobjectForBindings, scopeObjectForBindings); qSwap(_qobject, instance); + qSwap(_propertyCache, cache); return errors.isEmpty(); } diff --git a/src/qml/qml/qqmlobjectcreator_p.h b/src/qml/qml/qqmlobjectcreator_p.h index a8907fb762..3c180c65f7 100644 --- a/src/qml/qml/qqmlobjectcreator_p.h +++ b/src/qml/qml/qqmlobjectcreator_p.h @@ -70,8 +70,7 @@ public: private: QObject *createInstance(int index, QObject *parent = 0); - bool populateInstance(int index, QObject *instance, QQmlRefPointer<QQmlPropertyCache> cache, - QObject *scopeObjectForJavaScript, QQmlPropertyData *valueTypeProperty); + bool populateInstance(int index, QObject *instance, QQmlRefPointer<QQmlPropertyCache> cache, QObject *bindingTarget, QQmlPropertyData *valueTypeProperty); void setupBindings(); bool setPropertyValue(QQmlPropertyData *property, int index, const QV4::CompiledData::Binding *binding); @@ -97,7 +96,9 @@ private: QQmlContextData *rootContext; QObject *_qobject; - QObject *_qobjectForBindings; + QObject *_scopeObject; + QObject *_bindingTarget; + QQmlPropertyData *_valueTypeProperty; // belongs to _qobjectForBindings's property cache const QV4::CompiledData::Object *_compiledObject; QQmlData *_ddata; diff --git a/src/qml/qml/v8/qv8engine.cpp b/src/qml/qml/v8/qv8engine.cpp index e64cc0c83b..aa3b7eeb34 100644 --- a/src/qml/qml/v8/qv8engine.cpp +++ b/src/qml/qml/v8/qv8engine.cpp @@ -300,7 +300,8 @@ QV4::ReturnedValue QV8Engine::fromVariant(const QVariant &variant) return QV4::JsonObject::fromJsonObject(m_v4Engine, *reinterpret_cast<const QJsonObject *>(ptr)); case QMetaType::QJsonArray: return QV4::JsonObject::fromJsonArray(m_v4Engine, *reinterpret_cast<const QJsonArray *>(ptr)); - + case QMetaType::QLocale: + return QQmlLocale::wrap(this, *reinterpret_cast<const QLocale*>(ptr)); default: break; } @@ -395,6 +396,8 @@ QVariant QV8Engine::toBasicVariant(const QV4::ValueRef value) return value->asDouble(); if (value->isString()) return value->stringValue()->toQString(); + if (QQmlLocaleData *ld = value->as<QQmlLocaleData>()) + return ld->locale; if (QV4::DateObject *d = value->asDateObject()) return d->toQDateTime(); // NOTE: since we convert QTime to JS Date, round trip will change the variant type (to QDateTime)! diff --git a/src/quick/scenegraph/coreapi/qsgbatchrenderer.cpp b/src/quick/scenegraph/coreapi/qsgbatchrenderer.cpp index c424fb2668..4e62f85d30 100644 --- a/src/quick/scenegraph/coreapi/qsgbatchrenderer.cpp +++ b/src/quick/scenegraph/coreapi/qsgbatchrenderer.cpp @@ -2116,6 +2116,10 @@ void Renderer::renderUnmergedBatch(const Batch *batch) if (g->drawingMode() == GL_LINE_STRIP || g->drawingMode() == GL_LINE_LOOP || g->drawingMode() == GL_LINES) glLineWidth(g->lineWidth()); +#if !defined(QT_OPENGL_ES_2) + else if (g->drawingMode() == GL_POINTS) + glPointSize(g->lineWidth()); +#endif if (g->indexCount()) glDrawElements(g->drawingMode(), g->indexCount(), g->indexType(), iOffset); diff --git a/src/quick/scenegraph/coreapi/qsggeometry.cpp b/src/quick/scenegraph/coreapi/qsggeometry.cpp index ffb11fc6fa..40e0a014ab 100644 --- a/src/quick/scenegraph/coreapi/qsggeometry.cpp +++ b/src/quick/scenegraph/coreapi/qsggeometry.cpp @@ -525,8 +525,9 @@ void QSGGeometry::setDrawingMode(GLenum mode) } /*! - Gets the current line width to be used for this geometry. This property only - applies where the drawingMode is GL_LINES or a related value. + Gets the current line or point width or to be used for this geometry. This property + only applies to line width when the drawingMode is \c GL_LINES, \c GL_LINE_STRIP, or + \c GL_LINE_LOOP, and only applies to point size when the drawingMode is \c GL_POINTS. The default value is \c 1.0 @@ -538,8 +539,9 @@ float QSGGeometry::lineWidth() const } /*! - Sets the line width to be used for this geometry to \a width. The line width - only applies where the drawingMode is \c GL_LINES or a related value. + Sets the line or point width to be used for this geometry to \a width. This property + only applies to line width when the drawingMode is \c GL_LINES, \c GL_LINE_STRIP, or + \c GL_LINE_LOOP, and only applies to point size when the drawingMode is \c GL_POINTS. \sa lineWidth(), drawingMode() */ diff --git a/tests/auto/qml/qqmllocale/tst_qqmllocale.cpp b/tests/auto/qml/qqmllocale/tst_qqmllocale.cpp index d565ad557c..0eb38d92e6 100644 --- a/tests/auto/qml/qqmllocale/tst_qqmllocale.cpp +++ b/tests/auto/qml/qqmllocale/tst_qqmllocale.cpp @@ -117,6 +117,7 @@ private slots: void stringLocaleCompare_data(); void stringLocaleCompare(); + void localeAsCppProperty(); private: void addPropertyData(const QString &l); QVariant getProperty(QObject *obj, const QString &locale, const QString &property); @@ -1223,6 +1224,41 @@ void tst_qqmllocale::stringLocaleCompare() QCOMPARE(obj->property("comparison").toInt(), QString::localeAwareCompare(string1, string2)); } +class Calendar : public QObject +{ + Q_OBJECT + Q_PROPERTY(QLocale locale READ locale WRITE setLocale) +public: + Calendar() { + } + + QLocale locale() const { + return mLocale; + } + + void setLocale(const QLocale &locale) { + mLocale = locale; + } +private: + QLocale mLocale; +}; + +void tst_qqmllocale::localeAsCppProperty() +{ + QQmlComponent component(&engine); + qmlRegisterType<Calendar>("Test", 1, 0, "Calendar"); + component.setData("import QtQml 2.2\nimport Test 1.0\nCalendar { locale: Qt.locale('en_GB'); property var testLocale }", QUrl()); + QVERIFY(!component.isError()); + QTRY_VERIFY(component.isReady()); + + Calendar *item = qobject_cast<Calendar*>(component.create()); + QCOMPARE(item->property("locale").toLocale().name(), QLatin1String("en_GB")); + + QVariant localeVariant(QLocale("nb_NO")); + item->setProperty("testLocale", localeVariant); + QCOMPARE(item->property("testLocale").toLocale().name(), QLatin1String("nb_NO")); +} + class DateFormatter : public QObject { Q_OBJECT |