Important: Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

Moving a figure



  • I created a triangle:

    QPainter painter(this);
    
      painter.setRenderHint(QPainter::Antialiasing);
      painter.setPen(QColor("#d4d4d4"));
    
    QRectF rect = QRectF(100, 50, 300, 100);
    
    
    
      QPainterPath path;
      painter.setBrush(QBrush("#D2691E"));
      path.moveTo(rect.left() + (rect.width()/2), rect.top());
      path.lineTo(rect.bottomLeft());
      path.lineTo(rect.bottomRight());
      path.lineTo(rect.left() + (rect.width() / 2), rect.top());
    
      painter.fillPath(path, QBrush(QColor ("#D2691E")));
    

    Now I want it to move smoothly on the x coordinate. How can I make it?


  • Lifetime Qt Champion

    Hi
    You can use the
    https://doc.qt.io/qt-5/animation-overview.html
    to move it around on screen but do notice that QWidgets are not that good for animations but
    if kept small it works fine.



  • @Demorald

    Create timer with X secs update invervall ( = movement speed) and add Y to x-pos every time your timer event happens

    @Demorald said in Moving a figure:

    smoothly

    Too short intervalls will produce a lot of re-drawing, too long intervalls will make your item "jump". So you'll need to test, what works best for you.



  • @Pl45m4

    I did this, here's the timer:

    Colours::Colours(QWidget *parent) :
        QDialog(parent),
        ui(new Ui::Colours)
    {
        ui->setupUi(this);
        QTimer *timer = new QTimer(this);
        connect(timer, SIGNAL(timeout()), this, SLOT(update()));
        timer->start(1000);
    }
    
    

    And redraw function:

    void Colours::redraw(int x)
    {
    
        QPainter painter(this);
        QRectF rect = QRectF(x, 50, 300, 100);
    
    
    
        QPainterPath path;
        painter.setBrush(QBrush("#D2691E"));
        path.moveTo(rect.left() + (rect.width()/2), rect.top());
        path.lineTo(rect.bottomLeft());
        path.lineTo(rect.bottomRight());
        path.lineTo(rect.left() + (rect.width() / 2), rect.top());
    
        painter.fillPath(path, QBrush(QColor ("#D2691E")));
    }
    

    I call this function from paintEvent and it does draw new triangles, but the previous ones aren't being removed, so i just get a line of triangles instead initial one moving. I guess i made a mistake in the timer and it does not update a widget, but i can't find out what to do


  • Lifetime Qt Champion

    @Demorald
    Hi
    Well you can use
    painter.drawRect(rect());
    with a brush set to clear it.



  • @Demorald

    Ahh... my bad... my suggestion works, if your triangle is a QWidget or QGraphicsItem, but you paint directly onto your canvas.

    So, yeah, re-paint the whole area first, as @mrjj said, and then paint your new updated triangle.



  • @Pl45m4
    @mrjj
    I'm not exactly sure, where should i put it? I tried putting it instead of update() in the timer or in the beginning of the redraw function, and it didn't work.. Just nothing happened in the timer case and in the function one the whole widget just became black. Seems like something in the logic has broken.

    
    void Colours::redraw(int x)
    {
        QPainter painter(this);
    
        painter.setBrush(QBrush("D2691E"));
    
        painter.drawRect(rect());
    
        QRectF rect = QRectF(x, 50, 300, 100);
    
        QPainterPath path;
        painter.setBrush(QBrush("#D2691E"));
        path.moveTo(rect.left() + (rect.width()/2), rect.top());
        path.lineTo(rect.bottomLeft());
        path.lineTo(rect.bottomRight());
        path.lineTo(rect.left() + (rect.width() / 2), rect.top());
    
        painter.fillPath(path, QBrush(QColor ("#D2691E")));
    }
    

  • Lifetime Qt Champion

    @Demorald
    That seems a good place. however, i think your color for the brush misses a #
    so its become invalid and hence black.


Log in to reply