Display a Personal Object (Draw a Circle) on QScrollArea & QGridLayOut



  • [EDITED THE SOURCE CODE]
    Hello everyone, I muss make the next design:

    http://postimg.org/image/6wobcaebv/

    I use QScrollArea & QGridLayOut, the problem comes, when I try add a personal widget, it not displayed.

    The widget is a simple circle, that change its color like a semaphore. I think that it's not well built .
    Please, any help or explanation will be well received

    Thanks in advance

    here is the code from the object (circle-semaphore)

    //ampel.h
    #ifndef AMPEL_H
    #define AMPEL_H
    #include <QWidget>
    
    
    
    class ampel : public QWidget
    {
    public:
        explicit ampel(QWidget *parent = 0, qint16 _maxX=1333, qint16 _maxY=768, qint16 _rad=40);
        void updatePos(int px=0, int py=0);
        void stateOn();
        void stateOFF();
        void stateError();
        void stateNotReaded();
    
    protected:
        void paintEvent(QPaintEvent *e);
    private:
        qint16 x,y,maxX,maxY,rad;
        QBrush *cColor = new QBrush;
        void doPainting();
    
    
    };
    
    #endif // AMPEL_H
    
    //************************************************
    //************************************************
    //ampel.cpp
    #include "ampel.h"
    #include <QPainter>
    
    ampel::ampel(QWidget *parent, qint16 _maxX, qint16 _maxY, qint16 _rad):
        QWidget(parent),maxX(_maxX),maxY(_maxY), rad(rad)
    {
        x=y=100;
        rad=_rad;
        cColor->setColor(Qt::gray);
        cColor->setStyle(Qt::SolidPattern);
        show();
    }
    //***********************************************
    void ampel::paintEvent(QPaintEvent *e){
        Q_UNUSED(e);
    
    
        resize(maxX,maxY);
        doPainting();
    
    }
    //***********************************************
    void ampel::doPainting(){
        QPainter dc(this);
    
        //QBrush circleColor(Qt::gray, Qt::SolidPattern);
        dc.setRenderHint(QPainter::Antialiasing,true);
        dc.setPen(QPen(Qt::black,3, Qt::DashLine, Qt::RoundCap));
        dc.setBrush(*cColor);// QBrush(Qt::green, Qt::SolidPattern)
        dc.drawEllipse(x,y,rad,rad);
    
    }
    //************************************************
    void ampel::updatePos(int px,int py){
        x=px;
        y=py;
    }
    //************************************************
    void ampel::stateOn(){
        cColor->setColor(Qt::green);
    
    }
    //************************************************
    void ampel::stateOFF(){
       cColor->setColor(Qt::black);
    }
    //************************************************
    void ampel::stateError(){
      cColor->setColor(Qt::red);
    }
    //************************************************
    void ampel::stateNotReaded(){
      cColor->setColor(Qt::gray);
    }
    

    And here, the code from the design in MainWindow

    //MainWindow.h
    #ifndef MAINWINDOW_H
    #define MAINWINDOW_H
    
    #include <QMainWindow>
    
    
    namespace Ui {
    class MainWindow;
    }
    
    class MainWindow : public QMainWindow
    {
        Q_OBJECT
    
    public:
        explicit MainWindow(QWidget *parent = 0);
        ~MainWindow();
    
    
    
    private:
        Ui::MainWindow *ui;
    };
    
    #endif // MAINWINDOW_H
    //*****************************************************
    //*****************************************************
    
    //MainWindow.cpp
    #include "mainwindow.h"
    #include "ui_mainwindow.h"
    #include <QLineEdit>
    #include<QVBoxLayout>
    #include<ampel.h>
    #include <QDebug>
    
    #define hLine       20 //height line
    #define cSize       15 //Approx Character Size with hLine 20
    #define wgC         2*cSize-0.3*cSize //width getChannel
    
    MainWindow::MainWindow(QWidget *parent) :
        QMainWindow(parent),
        ui(new Ui::MainWindow)
    {
        ui->setupUi(this);
        setFixedSize(1333,768);
    
    
        const qint8 rad = 15;
        ampel *circle0[15];
        for(qint8 i= 0; i < 15;i++){ 
            circle0[i] = new ampel(this,1333,768,rad); //<---------//Here paint 15 circles
       //     circle[i]->show();
       //     circle[i]->resize(100,100); //resize, do not work
            circle0[i]->updatePos(rad*i,rad*i);
        }
    
        QGridLayout *grid = new QGridLayout();
    
        ampel *circle[15];
        QLineEdit *channel[15], *timeOut[15], *canID[15];
    
        for(qint8 i= 0; i < 15;i++){
            circle[i] = new ampel(this,1333,768,5); <---here do not paint!!!!
            circle[i]->show();
            circle[i]->resize(100,100);
            channel[i] = new QLineEdit();
            timeOut[i] = new QLineEdit();
            canID[i] = new QLineEdit();
    
    
            grid->addWidget(circle[i],i,0);
            grid->addWidget(channel[i],i,1);
            grid->addWidget(timeOut[i],i,2);
            grid->addWidget(canID[i],i,3);
        }
    
        ui->scrollContents->setLayout(grid);
      //  channel[2]->setText("prueba");
      //  timeOut[3]->setText("timeout");
    
    
    
    }
    
    MainWindow::~MainWindow()
    {
        delete ui;
    }
    
    

  • Qt Champions 2016

    Hi, do you call ->show() on your Circles?
    after u insert them into the layout?
    Also, you are sure they have a size? w,h



  • @mrjj first: thank you
    I'm sorry, the call to circle is: circle[i] = new ampel(this,1333,768); I have the post edited, but the circle do not show :-(


  • Qt Champions 2016

    @yczo said:

    circle[i]

    The scrolling is really awful so not sure , but I dont see
    circle[i]->Show() ?

    It might just be not shown.

    what is its size?
    can u please make sure it has size.
    Height and Width.

    Just for test, can we try this :

    for(qint8 i= 0; i < 15;i++){
        circle[i] = new ampel(this,1333,768);
        circle[i]->show();
        circle[i]->resize(100,100); ...(rest)
    

    ....



  • for(qint8 i= 0; i < 15;i++){
    circle[i] = new ampel(this,1333,768);
    circle[i]->show();

    this does not work :-(


  • Qt Champions 2016

    @yczo
    ok, also try the resize(100,100)!

    well u need to find out if its due not being paint or what the heck is going on.

    Make small sample and insert you ampel there as
    the only widget and see if u can make it show.

    Normally its not issue to make it show. so its something really simple.



  •     circle[i] = new ampel(this,1333,768);
        circle[i]->show();
        circle[i]->resize(100,100);
    

    don't works.
    It could not be because the object handles another layer?

    regards


  • Qt Champions 2016

    @yczo

    Impossible to say.
    Maybe u cover it or maybe ur paint dont work.
    You should test your custom widget in a test project where
    NOTHING else could disturbed it.

    That way u know if it can even paint itself.

    ampel * circle = new ampel(this,1333,768);
    circle->show();
    circle->resize(100,100);

    should be enough in test project.

    Code do look fine as was as i can overview it.



  • @mrjj The next code works, but not into the QScrollArea, and invalidate it, the focus is blocked. (i have changed the object, for send the radius ).

    MainWindow::MainWindow(QWidget *parent) :
    QMainWindow(parent),
    ui(new Ui::MainWindow)

    {
        ui->setupUi(this);
        setFixedSize(1333,768);
    
    
        const qint8 rad = 15;
        ampel *circle0[15];
        for(qint8 i= 0; i < 15;i++){  //<-------here show 15 circles
            circle0[i] = new ampel(this,1333,768,rad);
       //     circle[i]->show(); //not necesary
       //     circle[i]->resize(100,100); //resize, do not work
            circle0[i]->updatePos(rad*i,rad*i);
        }
    
        QGridLayout *grid = new QGridLayout();
    
        ampel *circle[15];
        QLineEdit *channel[15], *timeOut[15], *canID[15];
    
        for(qint8 i= 0; i < 15;i++){
            circle[i] = new ampel(this,1333,768,5); //<--------here do not show nothing
            circle[i]->show();
            circle[i]->resize(100,100);
            channel[i] = new QLineEdit();
            timeOut[i] = new QLineEdit();
            canID[i] = new QLineEdit();
    
    
            grid->addWidget(circle[i],i,0);
            grid->addWidget(channel[i],i,1);
            grid->addWidget(timeOut[i],i,2);
            grid->addWidget(canID[i],i,3);
        }
    
        ui->scrollContents->setLayout(grid);
      //  channel[2]->setText("prueba");
      //  timeOut[3]->setText("timeout");
    }
    

  • Qt Champions 2016

    hi
    Ok, so now they show?
    what u mean by focus is blocked?



  • @mrjj That I can not scroll down the slider of QScrollArea.
    The circles shown outside QScroll area, but not inside


  • Qt Champions 2016

    @yczo said:

    grid->addWidget(circle[i],i,0);

    but you add to grid?
    That grid is in scrollarea?
    How can it be outside?
    The other objects u add, they are inside?



  • @mrjj Yes, but don't shows. i think that the problem come from the way of generate the circle with absolute coordinates:

    dc.drawEllipse(x,y,rad,rad);
    

    x,y (absolute)

    but i don't know another way, to make it.
    Is There another method?

    Regards


  • Qt Champions 2016

    @yczo
    Hi it cant be absolute!
    It will be relative to your self so the area
    is 0,0, width, height !

    You draw inside. so u cannot ! use global x,y
    you must move whole object! and it draws internal from 0,0

    so
    dc.drawEllipse(x,y,rad,rad);
    x,y can never be more than width / height :)



  • @mrjj
    We have a small misunderstanding, the new program draw twice, 15 circles out QScroll and should draw another 15 inside, but the last, don't make, just draw the first 15 created on mainwindow

    Greetings.


  • Qt Champions 2016

    ok so it does draw and all is as you except ?
    except the last is not inside the layout/scrollbox?

    Do u make these really big ?
    new ampel(this,1333,768,5);

    is it 1333 x 768 ???



  • @mrjj 1333x768 is the size of layout where is permitted to draw


  • Qt Champions 2016

    @yczo

    but if u must draw that big, it means u make the
    Widget so big ?

    How big are the circle widgets?????

    You can not draw outside the widget.



  • @mrjj Here is a hint: http://www.scriptscoop2.com/t/787129021050/qt-draw-inside-qscrollarea-in-a-qdialog.html

    but i don't know how to:

    Create another class which inherits QWidget. Override the paintEvent() method and to the painting you mention. Then, add the widget to the scroll area in your dialog.
    
    MyDialog::MyDialog()
    {
      QScrollArea *pScrl = new QScrollArea(this);
      pScrl->setWidget(new MyWidget(pScrl));
      ... // use a layout to put the scroll area in the dialog
    }
    
    To really make it useful you will need to resize the MyWidget instance to the size of the circle that you want to draw.
    

    Please can anybody help me? With a example?

    Greetings


Log in to reply
 

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