Example #1
0
/*!
    Return the name of this QML property.
*/
QString QDeclarativeProperty::name() const
{
    if (!d->isNameCached) {
        // ###
        if (!d->object) {
        } else if (d->isValueType()) {
            QString rv = d->core.name(d->object) + QLatin1Char('.');

            QDeclarativeEnginePrivate *ep = d->engine?QDeclarativeEnginePrivate::get(d->engine):0;
            QDeclarativeValueType *valueType = 0;
            if (ep) valueType = ep->valueTypes[d->core.propType];
            else valueType = QDeclarativeValueTypeFactory::valueType(d->core.propType);
            Q_ASSERT(valueType);

            rv += QString::fromUtf8(valueType->metaObject()->property(d->valueType.valueTypeCoreIdx).name());

            if (!ep) delete valueType;

            d->nameCache = rv;
        } else if (type() & SignalProperty) {
            QString name = QLatin1String("on") + d->core.name(d->object);
            name[2] = name.at(2).toUpper();
            d->nameCache = name;
        } else {
            d->nameCache = d->core.name(d->object);
        }
        d->isNameCached = true;
    }

    return d->nameCache;
}
QDeclarativeValueType *QDeclarativeValueTypeFactory::valueType(int t)
{
    QDeclarativeValueType *rv = 0;

    switch (t) {
    case QVariant::Point:
        rv = new QDeclarativePointValueType;
        break;
    case QVariant::PointF:
        rv = new QDeclarativePointFValueType;
        break;
    case QVariant::Size:
        rv = new QDeclarativeSizeValueType;
        break;
    case QVariant::SizeF:
        rv = new QDeclarativeSizeFValueType;
        break;
    case QVariant::Rect:
        rv = new QDeclarativeRectValueType;
        break;
    case QVariant::RectF:
        rv = new QDeclarativeRectFValueType;
        break;
    case QVariant::Vector2D:
        rv = new QDeclarativeVector2DValueType;
        break;
    case QVariant::Vector3D:
        rv = new QDeclarativeVector3DValueType;
        break;
    case QVariant::Vector4D:
        rv = new QDeclarativeVector4DValueType;
        break;
    case QVariant::Quaternion:
        rv = new QDeclarativeQuaternionValueType;
        break;
    case QVariant::Matrix4x4:
        rv = new QDeclarativeMatrix4x4ValueType;
        break;
    case QVariant::EasingCurve:
        rv = new QDeclarativeEasingValueType;
        break;
    case QVariant::Font:
        rv = new QDeclarativeFontValueType;
        break;
    default:
        break;
    }

    Q_ASSERT(!rv || rv->metaObject()->propertyCount() < 32);
    return rv;
}
Example #3
0
/*!
    Returns the type name of the property, or 0 if the property has no type
    name.
*/
const char *QDeclarativeProperty::propertyTypeName() const
{
    if (d->isValueType()) {

        QDeclarativeEnginePrivate *ep = QDeclarativeEnginePrivate::get(d->context);
        QDeclarativeValueType *valueType = 0;
        if (ep) valueType = ep->valueTypes[d->core.propType];
        else valueType = QDeclarativeValueTypeFactory::valueType(d->core.propType);
        Q_ASSERT(valueType);

        const char *rv = valueType->metaObject()->property(d->valueType.valueTypeCoreIdx).typeName();

        if (!ep) delete valueType;

        return rv;
    } else if (d->object && type() & Property && d->core.isValid()) {
        return d->object->metaObject()->property(d->core.coreIndex).typeName();
    } else {
        return 0;
    }
}
Example #4
0
QVariant QDeclarativePropertyPrivate::readValueProperty()
{
    if (isValueType()) {

        QDeclarativeEnginePrivate *ep = QDeclarativeEnginePrivate::get(context);
        QDeclarativeValueType *valueType = 0;
        if (ep) valueType = ep->valueTypes[core.propType];
        else valueType = QDeclarativeValueTypeFactory::valueType(core.propType);
        Q_ASSERT(valueType);

        valueType->read(object, core.coreIndex);

        QVariant rv =
            valueType->metaObject()->property(this->valueType.valueTypeCoreIdx).read(valueType);

        if (!ep) delete valueType;
        return rv;

    } else if (core.flags & QDeclarativePropertyCache::Data::IsQList) {

        QDeclarativeListProperty<QObject> prop;
        void *args[] = { &prop, 0 };
        QMetaObject::metacall(object, QMetaObject::ReadProperty, core.coreIndex, args);
        return QVariant::fromValue(QDeclarativeListReferencePrivate::init(prop, core.propType, engine)); 

    } else if (core.flags & QDeclarativePropertyCache::Data::IsQObjectDerived) {

        QObject *rv = 0;
        void *args[] = { &rv, 0 };
        QMetaObject::metacall(object, QMetaObject::ReadProperty, core.coreIndex, args);
        return QVariant::fromValue(rv);

    } else {

        return object->metaObject()->property(core.coreIndex).read(object.data());

    }
}
int QDeclarativeVMEMetaObject::metaCall(QMetaObject::Call c, int _id, void **a)
{
    int id = _id;
    if(c == QMetaObject::WriteProperty) {
        int flags = *reinterpret_cast<int*>(a[3]);
        if (!(flags & QDeclarativePropertyPrivate::BypassInterceptor)
            && !aInterceptors.isEmpty()
            && aInterceptors.testBit(id)) {
            QPair<int, QDeclarativePropertyValueInterceptor*> pair = interceptors.value(id);
            int valueIndex = pair.first;
            QDeclarativePropertyValueInterceptor *vi = pair.second;
            int type = property(id).userType();

            if (type != QVariant::Invalid) {
                if (valueIndex != -1) {
                    QDeclarativeEnginePrivate *ep = ctxt?QDeclarativeEnginePrivate::get(ctxt->engine):0;
                    QDeclarativeValueType *valueType = 0;
                    if (ep) valueType = ep->valueTypes[type];
                    else valueType = QDeclarativeValueTypeFactory::valueType(type);
                    Q_ASSERT(valueType);

                    valueType->setValue(QVariant(type, a[0]));
                    QMetaProperty valueProp = valueType->metaObject()->property(valueIndex);
                    vi->write(valueProp.read(valueType));

                    if (!ep) delete valueType;
                    return -1;
                } else {
                    vi->write(QVariant(type, a[0]));
                    return -1;
                }
            }
        }
    }
    if(c == QMetaObject::ReadProperty || c == QMetaObject::WriteProperty) {
        if (id >= propOffset) {
            id -= propOffset;

            if (id < metaData->propertyCount) {
               int t = (metaData->propertyData() + id)->propertyType;
                bool needActivate = false;

                if (t == -1) {

                    if (c == QMetaObject::ReadProperty) {
                        *reinterpret_cast<QVariant *>(a[0]) = readVarPropertyAsVariant(id);
                    } else if (c == QMetaObject::WriteProperty) {
                        writeVarProperty(id, *reinterpret_cast<QVariant *>(a[0]));
                    }

                } else {

                    if (c == QMetaObject::ReadProperty) {
                        switch(t) {
                        case QVariant::Int:
                            *reinterpret_cast<int *>(a[0]) = data[id].asInt();
                            break;
                        case QVariant::Bool:
                            *reinterpret_cast<bool *>(a[0]) = data[id].asBool();
                            break;
                        case QVariant::Double:
                            *reinterpret_cast<double *>(a[0]) = data[id].asDouble();
                            break;
                        case QVariant::String:
                            *reinterpret_cast<QString *>(a[0]) = data[id].asQString();
                            break;
                        case QVariant::Url:
                            *reinterpret_cast<QUrl *>(a[0]) = data[id].asQUrl();
                            break;
                        case QVariant::Color:
                            *reinterpret_cast<QColor *>(a[0]) = data[id].asQColor();
                            break;
                        case QVariant::Date:
                            *reinterpret_cast<QDate *>(a[0]) = data[id].asQDate();
                            break;
                        case QVariant::DateTime:
                            *reinterpret_cast<QDateTime *>(a[0]) = data[id].asQDateTime();
                            break;
                        case QMetaType::QObjectStar:
                            *reinterpret_cast<QObject **>(a[0]) = data[id].asQObject();
                            break;
                        default:
                            break;
                        }
                        if (t == qMetaTypeId<QDeclarativeListProperty<QObject> >()) {
                            int listIndex = data[id].asInt();
                            const List *list = &listProperties.at(listIndex);
                            *reinterpret_cast<QDeclarativeListProperty<QObject> *>(a[0]) = 
                                QDeclarativeListProperty<QObject>(object, (void *)list,
                                                                  list_append, list_count, list_at, 
                                                                  list_clear);
                        }

                    } else if (c == QMetaObject::WriteProperty) {

                        switch(t) {
                        case QVariant::Int:
                            needActivate = *reinterpret_cast<int *>(a[0]) != data[id].asInt();
                            data[id].setValue(*reinterpret_cast<int *>(a[0]));
                            break;
                        case QVariant::Bool:
                            needActivate = *reinterpret_cast<bool *>(a[0]) != data[id].asBool();
                            data[id].setValue(*reinterpret_cast<bool *>(a[0]));
                            break;
                        case QVariant::Double:
                            needActivate = *reinterpret_cast<double *>(a[0]) != data[id].asDouble();
                            data[id].setValue(*reinterpret_cast<double *>(a[0]));
                            break;
                        case QVariant::String:
                            needActivate = *reinterpret_cast<QString *>(a[0]) != data[id].asQString();
                            data[id].setValue(*reinterpret_cast<QString *>(a[0]));
                            break;
                        case QVariant::Url:
                            needActivate = *reinterpret_cast<QUrl *>(a[0]) != data[id].asQUrl();
                            data[id].setValue(*reinterpret_cast<QUrl *>(a[0]));
                            break;
                        case QVariant::Color:
                            needActivate = *reinterpret_cast<QColor *>(a[0]) != data[id].asQColor();
                            data[id].setValue(*reinterpret_cast<QColor *>(a[0]));
                            break;
                        case QVariant::Date:
                            needActivate = *reinterpret_cast<QDate *>(a[0]) != data[id].asQDate();
                            data[id].setValue(*reinterpret_cast<QDate *>(a[0]));
                            break;
                        case QVariant::DateTime:
                            needActivate = *reinterpret_cast<QDateTime *>(a[0]) != data[id].asQDateTime();
                            data[id].setValue(*reinterpret_cast<QDateTime *>(a[0]));
                            break;
                        case QMetaType::QObjectStar:
                            needActivate = *reinterpret_cast<QObject **>(a[0]) != data[id].asQObject();
                            data[id].setValue(*reinterpret_cast<QObject **>(a[0]));
                            break;
                        default:
                            break;
                        }
                    }

                }

                if (c == QMetaObject::WriteProperty && needActivate) {
                    activate(object, methodOffset + id, 0);
                }

                return -1;
            }

            id -= metaData->propertyCount;

            if (id < metaData->aliasCount) {

                QDeclarativeVMEMetaData::AliasData *d = metaData->aliasData() + id;

                if (d->flags & QML_ALIAS_FLAG_PTR && c == QMetaObject::ReadProperty) 
                        *reinterpret_cast<void **>(a[0]) = 0;

                if (!ctxt) return -1;

                QDeclarativeContext *context = ctxt->asQDeclarativeContext();
                QDeclarativeContextPrivate *ctxtPriv = QDeclarativeContextPrivate::get(context);

                QObject *target = ctxtPriv->data->idValues[d->contextIdx].data();
                if (!target) 
                    return -1;

                connectAlias(id);

                if (d->isObjectAlias()) {
                    *reinterpret_cast<QObject **>(a[0]) = target;
                    return -1;
                } 
                
                // Remove binding (if any) on write
                if(c == QMetaObject::WriteProperty) {
                    int flags = *reinterpret_cast<int*>(a[3]);
                    if (flags & QDeclarativePropertyPrivate::RemoveBindingOnAliasWrite) {
                        QDeclarativeData *targetData = QDeclarativeData::get(target);
                        if (targetData && targetData->hasBindingBit(d->propertyIndex())) {
                            QDeclarativeAbstractBinding *binding = QDeclarativePropertyPrivate::setBinding(target, d->propertyIndex(), d->isValueTypeAlias()?d->valueTypeIndex():-1, 0);
                            if (binding) binding->destroy();
                        }
                    }
                }
                
                if (d->isValueTypeAlias()) {
                    // Value type property
                    QDeclarativeEnginePrivate *ep = QDeclarativeEnginePrivate::get(ctxt->engine);

                    QDeclarativeValueType *valueType = ep->valueTypes[d->valueType()];
                    Q_ASSERT(valueType);

                    valueType->read(target, d->propertyIndex());
                    int rv = QMetaObject::metacall(valueType, c, d->valueTypeIndex(), a);
                    
                    if (c == QMetaObject::WriteProperty)
                        valueType->write(target, d->propertyIndex(), 0x00);

                    return rv;

                } else {
                    return QMetaObject::metacall(target, c, d->propertyIndex(), a);
                }

            }
            return -1;

        }

    } else if(c == QMetaObject::InvokeMetaMethod) {

        if (id >= methodOffset) {

            id -= methodOffset;
            int plainSignals = metaData->signalCount + metaData->propertyCount +
                               metaData->aliasCount;
            if (id < plainSignals) {
                QMetaObject::activate(object, _id, a);
                return -1;
            }

            id -= plainSignals;

            if (id < metaData->methodCount) {
                if (!ctxt->engine)
                    return -1; // We can't run the method

                QDeclarativeEnginePrivate *ep = QDeclarativeEnginePrivate::get(ctxt->engine);

                QScriptValue function = method(id);

                QScriptValueList args;
                QDeclarativeVMEMetaData::MethodData *data = metaData->methodData() + id;
                if (data->parameterCount) {
                    for (int ii = 0; ii < data->parameterCount; ++ii) {
                        args << ep->scriptValueFromVariant(*(QVariant *)a[ii + 1]);
                    }
                }
                QScriptValue rv = function.call(ep->objectClass->newQObject(object), args);

                if (a[0]) *reinterpret_cast<QVariant *>(a[0]) = ep->scriptValueToVariant(rv);

                return -1;
            }
            return -1;
        }
    }

    if (parent)
        return parent->metaCall(c, _id, a);
    else
        return object->qt_metacall(c, _id, a);
}