Using a macro to access and application name.



  • While working on a plug-in for Maya I ran across this snip-it of code and was hoping to find out exactly what it does and how I might be able to use it.
    @QCoreApplication* app = qApp;@

    According to my understanding there can only be one application object. What I would like to do is to use something like:
    @QDeclarativeView view;
    view.setSource(QUrl("qrc:/myCustomUI.qml"));
    view.show();
    return app.exec();@

    My problem is that I cant figure out how to use them together to display my "myCustomUI.qml".



  • qApp is a simple preprocessor macro that basically expands to the static method "QCoreApplication::instance()":http://developer.qt.nokia.com/doc/qt-4.8/qcoreapplication.html#instance with some cast glue so that you will get QApplication* for GUI applications and QCoreApplication* for console applications.
    @
    return qApp->exec();
    @
    If you are using Qt Creator just use Follow Symbol Under Cursor or F2 to get to the definition.



  • O so here is what I tried. (Please excuse my lack of understanding here as I am just getting my feet wet with QT and c++)
    @int myFunc(){
    QCoreApplication* app = qApp;
    QDeclarativeView view;
    view.setSource(QUrl("qrc:/myQMl.qml"));
    view.show();
    return qApp->exec();

    }@

    What keeps happening is that it goes through my function and displays my UI for a split second and then closes. I have a feeling it is not waiting around once it gets to return qApp->exec(). Any ideas?



  • Your QApplication (not QCoreApplication) is declared elsewhere and qApp does not return null, does it?

    exec() should not return unless exit() is called (either directly or indirectly through eg. quit()).

    Just add a breakpoint at <code>return qApp->exec()</code> and step over / step through to find out what happens.

    Keep in mind that things might be different for you as you do not create a Qt application directly but extend an existing one, so there might be an already running event loop. If so - and exec() returns immediately - your widget closes after a split second because it is created on the stack and thus goes out of scope as soon as <code>myFunc()</code> is left. This can be solved by creating <code>view</code> on the heap instead, which feels more correct to me anyways.

    I'm quite sure Maya provides documentation on how to create plugins, including examples. I would start right there.



  • Calling exec on a QApplication instance a second time returns immediately and causes a warning on the console:

    bq. QCoreApplication::exec: The event loop is already running

    As the QDeclarativeView is stack based, it is deleted as soon as myFunc returns. The latter doesn't block - exec returns immediately - and thus the view is nuked immediately too.



  • Thanks for the responses its all starting to make a bit more sense now. But how does one go about adding a view onto the heap. After digging around for a couple of hours I haven't been able to find much on how to do this, with the exception of this snip-it which seems to be adding a QApplication to the heap.

    @int main(int argc, char ** argv)
    {
    QApplication * pApp = new QApplication(argc, argv)
    ......
    delete pApp;
    }@

    But I cant seem to make sense of it in my context since my function is not "int main" and I am not passing "(int argc, char ** argv)" . Thanks again for all your help in pointing me in the right direction.



  • [quote author="Cg_Artist" date="1327601596"]Thanks for the responses its all starting to make a bit more sense now. But how does one go about adding a view onto the heap. After digging around for a couple of hours I haven't been able to find much on how to do this, with the exception of this snip-it which seems to be adding a QApplication to the heap.[/quote]

    Honestly, you should start with a good book on C++ then. Qt is actually quite easy to learn, but it still requires a basic knowledge of C++.



  • Yes I am a newbie :-) but what I think I'm missing is what I should instantiate a new instance of the QApplication with?

    docs says : argc must be greater than zero and argv must contain at least one valid character string.

    Only one application object should be created. ( whick I understand how to referance QCoreApplication* app = qApp; )

    Thanks for any help.

    Cheers!



  • If you are writing a plugin for an application that already uses Qt you most probably should not create an additional QApplication object at all.

    Your best bet would be referring to the Maya documentation - after you have mastered the basics of C++ and after you have mastered the basics of Qt. Trust me, there's not shortcut to that, at least none that doesn't end in pure frustration.



  • Found the solution: See below.



  • So yes ... I am back with the solution for those of you who don't don't use QT for a living like Mr. Lukas and are still interested in how things work. As Volker pointed out the QDeclarativeView, as every other GUI class, must live in the main thread. That is why the following code does not work:
    @int main(int argc, char ** argv)
    {
    QCoreApplication* app = qApp;
    return qApp->exec();
    return app.exec();
    }@

    Strange looking code I know but I tried it. :) Basically, in layman terms we are trying to run an application within an application using the same memory space. (Or some thing like that). Definitely not the correct way to do things. So what can we do, well there's...
    @ int main(int argc, char *argv[])
    {
    QApplication app(argc, argv);

     QDeclarativeView view;
     view.setSource(QUrl::fromLocalFile&#40;"application.qml"&#41;&#41;;
     view.show(&#41;;
    
     return app.exec&#40;&#41;;
    

    }@

    This works but keep in mind that this creates the QDeclarativeView instance as a variable on the stack.
    However if you use the code:
    @int main(int argc, char *argv[])
    {
    QApplication app(argc, argv);
    QDeclarativeView *qmlView = new QDeclarativeView;
    qmlView->setSource(QUrl::fromLocalFile("myQML.qml"));
    qmlView->show();
    return app.exec();
    }@

    the QDeclarativeView is not instanced on the stack rather on what I think Lukas was referring to as the "heap". (The heap is the name for a block of RAM that is used to store dynamic variables). One thing to keep in mind is that in the first example the QDeclarativeView instance is automatically destroyed when the function terminates, but in the second example we can use delete on a main window when we have finished with it to save memory.

    So to reference my particular situation there was already and event loop which had been started by Maya. So all I had to do was add this to my function:
    @int myFunction(){
    QDeclarativeView *qmlView = new QDeclarativeView;
    qmlView->setSource(QUrl::fromLocalFile("myQML.qml"));
    qmlView->show();
    }@

    And that's pretty much it. :) Hopefully others will find this information more helpful then just telling them to go get an education. :)


Log in to reply
 

Looks like your connection to Qt Forum was lost, please wait while we try to reconnect.