QWidget & inheritance



  • Hi
    I have a QWidget (pointer) and I want to change it in runtime to different widgets that inherit QWidget. I want to be able to use the new widget's functions but I can't do it. can anyone help?
    Thanks in advance.

    QWidget *widget;

    widget = new QProgressBar();

    widget->setRange(0,100); //Error (the function not recognized)



  • To make this work, you will have to convert the pointer to your widget first, e.g.

    QProgressBar *p = qobject_cast<QProgressBar *>(widget);
    if(p)
      p->setRange(...);
    

    If you want to do something similar with other types of widgets (QLabel, QSlider, ...), you would have to convert the pointer every time you want to call a function that is not virtual in QWidget itself. I.e.

    QWidget *widget;
    widget = new QLabel();
    
    widget->sizeHint();//works, since QWidgets implementation has been overridden in QLabel
    widget->setText("...");//does *not* work since you are calling this method on a QWidget!
    QLabel *l = qobject_cast<QLabel *>(widget);
    if(l)
      l->setText("...");//works, since you are explicitely calling QLabels implementation of the method
    


  • Hi @thEClaw
    what if I want to delete the widget that is a QProgressbar after a while? if I delete the widget, the new pointer that is a QProgressBar is deleted too?


  • Moderators

    If you delete the object your pointer is pointing to then the object will be deleted even if it is QProgressBar:

    QWidget *widget;
    widget = new QProgressBar();
    delete widget; // Will delete QProgressBar
    

    As far as I know Qt uses virtual destructors for base classes, so even if the pointer is of base class type the correct destructor will be called.


  • Qt Champions 2016

    @jsulm said:

    As far as I know Qt uses virtual destructors for base classes

    Yes. QObject's destructor is virtual. Classes that derive from other bases might not have a virtual destructor, though (e.g. QStringList, not that you would want to create that in the heap).

    @shahriar25

    I have a QWidget (pointer) and I want to change it in runtime to different widgets that inherit QWidget. I want to be able to use the new widget's functions but I can't do it. can anyone help?

    You can, as @thEClaw has show, however the rationale behind that somewhat escapes me. Why do you want to do that?



  • Hi @kshegunov
    I want the user to enter the widget's name an the program to show that widget and change it by entering sth.


  • Qt Champions 2016

    @shahriar25
    This is a very unusual requirement. I doubt qobject_cast will help you for this, though. You probably want to create objects by class name, which is possible through the meta-object system, however it's a bit hackish. Something along the lines of:

    QWidget * parent; // The parent of the widget we are creating
    
    QByteArray className = QByteArrayLiteral("QDialog*");
    int typeId = QMetaType::type(className);
    if (typeId == 0)
        ; // Error - class is not registered
    
    //< Here is needed an additional check if that class actually derives from QObject
    
    const QMetaObject * metaObject = QMetaType::metaObjectForType(typeId);
    QObject * widget = metaObject->newInstance(Q_ARG(QWidget *, parent));
    

    But why do you need to do that in the first place?



  • @kshegunov
    wow your code really creates an object by it's name. this is an interesting thing. but this is not what I want. my program get predefined commands from user or an external program and does something specific. the commands are limited and I want to create about 10 widgets one at a time. so thEClaw's answer is enough here. thank you all


  • Qt Champions 2016

    @shahriar25 said:

    wow your code really creates an object by it's name.

    It should, but I can't claim merit for it. I think I read about that approach some time ago in the mailing list.

    but this is not what I want. my program get predefined commands from user or an external program and does something specific.

    I see. Then I must have misunderstood you. But in any case, I'm glad it worked out in the end.



  • Yes of course but only with your help this becomes possible


Log in to reply
 

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