Welcome!

Welcome to the official BlackBerry Support Community Forums.

This is your resource to discuss support topics with your peers, and learn from each other.

inside custom component

Native Development

Reply
Developer
Posts: 326
Registered: ‎02-02-2009
My Device: Not Specified
Accepted Solution

Q_PROPERTY

I am confused about Q_PROPERTY

can any body explain what "Q_PROPERTY(QString text READ text WRITE setText NOTIFY textChanged)" means

Developer
Posts: 16,786
Registered: ‎07-29-2008
My Device: Z10 LE, Z30, Passport
My Carrier: O2 Germany

Re: Q_PROPERTY

you should read this:
https://developer.blackberry.com/native/documentation/cascades/dev/integrating_cpp_qml/index.html

the property means that you can access the value by using objectName.property, in this case .text, in QML.
you can assign a value in qml and the c++ class will be called with setText, and you can use onTextChanged in QML which will called when you emit textChanged from c++ (for example from setText).

this may also be an helpful overview:
http://www.developer.nokia.com/Community/Wiki/How_to_use_Q_PROPERTY
----------------------------------------------------------
feel free to press the like button on the right side to thank the user that helped you.
please mark posts as solved if you found a solution.
@SimonHain on twitter
Developer
Posts: 1,523
Registered: ‎12-18-2012
My Device: Z30, Z10 LE, DevAlpha C, PlayBook

Re: Q_PROPERTY

Hi,

 

It allows exposing properties to QML by defining a getter, a setter and a signal which is emitted when the property is changed. A typical implementation looks like this:

 

.h file:

public:
  Q_PROPERTY(int categoryId READ categoryId WRITE setCategoryId NOTIFY categoryIdChanged)

  int categoryId() const { return categoryId_; }
  void setCategoryId(int categoryId);

signals:
  void categoryIdChanged(int categoryId);

 

.cpp file:

Constructor:

ClassName::ClassName()
  : QObject(...)
  , categoryId_(0)
{
  ...
}

...

void ClassName::setCategoryId(int categoryId)
{
  if (categoryId_ == categoryId)
    return;
  categoryId_ = categoryId;
  emit categoryIdChanged(categoryId_);
}

Now if the class is exported to QML, the property can be referenced like this:

 

item.categoryId = ...;

or

ClassName {
  onCategoryIdChanged: {
    do something with categoryId
  }
}

For more information, please see this page:

http://developer.blackberry.com/native/reference/cascades/properties.html

 


Andrey Fidrya, @zmeyc on twitter
Retired
Posts: 571
Registered: ‎06-25-2010
My Device: Z10
My Carrier: Vodafone

Re: Q_PROPERTY

[ Edited ]

Hi

 

Q_PROPERTY is a macro and part of the Qt properties system. Its purpose is to allow us to bind properties that we use in our QML to C++ data via suitable methods. Your example associates three things with a QML property whose id is "text". Let's review each of them:

 

READ text: this means "to obtain a value for the text property, call a C++ method text()"

 

WRITE setText: this means "if we change the value of the text property in QML by assigning a value to it, communicate this to C++ by calling a method setText(QString new_text)"

 

NOTIFY textChanged: this means "if the value of the data in my C++ object is changed by some non-QML action, notify me that it has changed so that I can update the property value in QML by emiting the Qt signal whose name is "textChanged()"

 

There's further information on integrating QML and C++ in our documentation here:

 

http://developer.blackberry.com/native/documentation/cascades/dev/integrating_cpp_qml/

 

Here's an example of my own as well:

 

Q_OBJECT

    // a Q_PROPERTY declaration is a binding between a property we can use in QML and underlying C++ methods and signals

Q_PROPERTY(
        // the name of our property as used from QML
        QString my_property
        // a method that will be called to populate our QML property with a value from C++
        READ getMyProperty
        // a method that will be called when we want to change the value of our corresponding C++ variable
        WRITE setMyProperty
        // a signal that will be emitted if the underlying data value changes. This signal will be automatically connected to our QML property
        // so that anywhere our property has been used, it's value will be updated
        NOTIFY signalMyPropertyChanged)

 Figure 1 declaring a Q_PROPERTY

 

 And then we declare the associated methods and signal:

 

public:

    // for my Q_PROPERTY
    QString getMyProperty();
    void setMyProperty(QString text);

    Q_INVOKABLE void resetMyProperty();

signals:
    // signal that is emitted if my property value changes
    void signalMyPropertyChanged();

 Figure 2: declaring methods and signals used by the Q_PROPERTY

 

private:
    QString _some_text;

 Figure 3: Our C++ data that we are binding to our property

 

Note I also used Q_INVOKABLE which makes the specified method resetMyProperty() directly callable from QML.

 

QString ApplicationUI::getMyProperty() {
    qDebug() << "XXXX getMyProperty called";
    return _some_text;
}

void ApplicationUI::setMyProperty(QString some_text) {
    qDebug() << "XXXX setMyProperty called:" << some_text;
    _some_text = some_text;
    qDebug() << "XXXX setMyProperty emiting signalMyPropertyChanged";
    emit signalMyPropertyChanged();
}

void ApplicationUI::resetMyProperty() {
    qDebug() << "XXXX resetMyProperty called";
    setMyProperty("Hello I am a property");
}

 Figure 4: Implementation of C++ functions

 

    QmlDocument *qml = QmlDocument::create("asset:///main.qml").parent(this);

    // expose the property to QML
    qml->setContextProperty("my_prop", this);

 Figure 5 expose our C++ object to QML

 

import bb.cascades 1.2

Page {
    Container {

        TextField {
            id: tf
            objectName: "tf"
            // this causes the READ method bound to our property to be called
            text: my_prop.my_property
        }
        Button {
            text: "Change Property"
            onClicked: {
                // this causes the WRITE method bound to our property to be called 
                my_prop.my_property = tf.text
            }
        }
        Button {
            text: "Reset"
            onClicked: {
                // this calls a C++ method that was exposed using Q_INVOKABLE
                my_prop.resetMyProperty();
            }
        }
    }
}

 Figure 6 The QML

 

 

When I run my app, I see that TextField tf is automatically populated and that this is accomplished by the system calling the READ method getMyProperty. Then, if I change the text and click the Change Property button, I see that the WRITE method is called. If I click Reset, the Q_INVOKABLE method is called directly from QML and it emits my signal, thus notifying the QML that the bound property value has changed. This causes a call to the READ method and my text field in QML gets updated.

 

XXXX getMyProperty called 
XXXX setMyProperty called: "Hello" 
XXXX setMyProperty emiting signalMyPropertyChanged 
XXXX getMyProperty called 
XXXX resetMyProperty called 
XXXX setMyProperty called: "Hello I am a property" 
XXXX setMyProperty emiting signalMyPropertyChanged 
XXXX getMyProperty called 

 Figure 7: console output showing calls 

 

Hope that helps

 

Martin

--------------------------------------------------------------------------------------------
Feel free to press the like button on the right side if you liked my attempts to help :-)
And please mark posts as solved if you think I found the solution or set you on its path. Thanks!
Follow me on Twitter: @mdwrim
Retired
Posts: 571
Registered: ‎06-25-2010
My Device: Z10
My Carrier: Vodafone

Re: Q_PROPERTY

I released my simple example application to Git Hub.

 

https://github.com/blackberry/Cascades-Community-Samples/tree/master/PropertyExample

 

Martin

--------------------------------------------------------------------------------------------
Feel free to press the like button on the right side if you liked my attempts to help :-)
And please mark posts as solved if you think I found the solution or set you on its path. Thanks!
Follow me on Twitter: @mdwrim
Developer
Posts: 16,786
Registered: ‎07-29-2008
My Device: Z10 LE, Z30, Passport
My Carrier: O2 Germany

Re: Q_PROPERTY

Martin is on a run here, nominating this thread for awesome support level status Smiley Happy
----------------------------------------------------------
feel free to press the like button on the right side to thank the user that helped you.
please mark posts as solved if you found a solution.
@SimonHain on twitter
Highlighted
Retired
Posts: 571
Registered: ‎06-25-2010
My Device: Z10
My Carrier: Vodafone

Re: Q_PROPERTY

Thanks Simon :-)

 

I do like this thread though. Look what happened! 

--------------------------------------------------------------------------------------------
Feel free to press the like button on the right side if you liked my attempts to help :-)
And please mark posts as solved if you think I found the solution or set you on its path. Thanks!
Follow me on Twitter: @mdwrim
Developer
Posts: 1,670
Registered: ‎04-08-2010
My Device: Z10 (red Limited Edition), Q10, Z30
My Carrier: Telekom.de, O2, Vodafone

Re: Q_PROPERTY

thats the real value of this forum and a great community Smiley Happy

-------------------------------------------------------------------------------
ekke (independent software architect, rosenheim, germany)

BlackBerry Elite Developer
BlackBerry Platinum Enterprise Partner
International Development Mobile Apps BlackBerry 10 Cascades
Cascades - Workshops / Trainings / Bootcamps

blog: http://ekkes-corner.org videos: http://www.youtube.com/user/ekkescorner http://vimeo.com/ekkescorner/videos
bb10-development: http://appbus.org Twitter: @ekkescorner