QAction *action = ~~~;
auto prop = action->text;
This already gives you the string. You cannot retrieve the property
itself. You can alternatively do action->text() or action->text.value().
They all do the same thing.

Uhm... sorry, no, this doesn't really compute for me. Ignore the copy semantics for a second (use const auto &, if necessary), what's decltype(prop)? If it's QString, then you can't write .value() after it.

OK, I got you wrong, and I was confused about the cast operators in QProperty and the property wrappers. Sorry. Indeed "auto prop = action->text;" would give you a useless object that pokes random memory whenever you invoke any method of it. That needs to be fixed indeed. You should not be able to copy the property wrapper out of the object. For properties on QObject that would be easy as QObject itself is not copyable. We could just =delete the copy ctor and assignment operators. We might also prevent external construction of the struct by having some "secret" extra argument, kind of like QPrivateSignal.

However, for Q_GADGET this would fall apart.

For reference, Q_PRIVATE_QPROPERTY looks like this:

#define Q_PRIVATE_QPROPERTY(accessor, type, name, setter, ...) \
            struct _qt_property_api_##name { \
                type value() const; \
                type operator()() const { return value(); } \
                void setValue(type &&); \
                void setValue(type const &); \
                void operator=(type const &v) { setValue(v); } \
                void operator=(type &&v) { setValue(std::move(v)); } \
QPropertyBinding<type> setBinding(const QPropertyBinding<type> &); \ QPropertyBinding<type> setBinding(QPropertyBinding<type> &&); \ QPropertyBinding<type> operator=(const QPropertyBinding<type> &b) { return setBinding(b); } \ QPropertyBinding<type> operator=(QPropertyBinding<type> &&b) { return setBinding(std::move(b)); } \
                bool setBinding(const QUntypedPropertyBinding &); \
                template <typename Functor> \
                QPropertyBinding<type> setBinding(Functor f, \
const QPropertyBindingSourceLocation &location = QT_PROPERTY_DEFAULT_BINDING_LOCATION) \
                { \
return setBinding(Qt::makePropertyBinding(f, location)); \
                } \
                bool hasBinding() const; \
                QPropertyBinding<type> binding() const; \
                QPropertyBinding<type> takeBinding(); \
            }; \
            void setter(type const& value);

So, in fact we need to rework this and provide only methods instead of a struct. Now we need a naming convention for all those methods and some way of avoiding name clashes.

If QNotifiedProperty didn't need members of the private object as template parameters, we could just have one extra method that retrieves a reference to the underlying Q(Notified)Property (or rather two: const and non-const).

No, actually this makes perfect sense, but was contradicted before:
We are not casting these structs to or from anything though, do we?

That statement was wrong. We do need to cast the structs. Another argument for eliminating them.

best,
Ulf
_______________________________________________
Development mailing list
Development@qt-project.org
https://lists.qt-project.org/listinfo/development

Reply via email to