Thalia
Thalia

Reputation: 14605

Moving an item with the mouse on QGraphicsView / QGraphicsScene

I have a QGraphicsView area that displays some Item items. I would like to have mouse move implemented.

class Item
{
public:
    Item();
    void update();
    int x, y; // position
    int z; // order - should correspond also to index in item list
};

class Collection : public QGraphicsView
{
Q_OBJECT
public:
    Collection(QWidget *parent = 0);
    void update();
    QList<Item> *m_items;
protected:
    virtual void paintEvent(QPaintEvent * event);
    virtual void mousePressEvent(QMouseEvent * event);
    virtual void mouseReleaseEvent(QMouseEvent *event);
private:
    QPoint offset;
    int itemMoved;
};

trying:

void Collection::mousePressEvent(QMouseEvent* event)
{
    Item *currentItem = NULL;
    itemMoved = -1;
    foreach (QGraphicsItem *item, this->items(event->pos()))
    {

// never get into this loop since my items are not children of QGraphicsItem

        currentItem = dynamic_cast<Item*>(item);
        if (event->button() == Qt::LeftButton && currentItem)
        {
            itemMoved = currentItem->z;
            offset = event->pos();
        }
        else if (event->button() == Qt::RightButton)
        {
            // set right click stuff
        }
        else
        {
            event->ignore();
        }
        break;
    }
}

void CollectionView::mouseReleaseEvent(QMouseEvent* event)
{
    if(event->button() == Qt::LeftButton && itemMoved > 0)
    {
        m_items->at(itemMoved).x = event->pos().x();
        m_items->at(itemMoved).y = event->pos().y();

// So far multiple fails:

//    error: assignment of data-member 'Item::x' in read-only structure
//    error: assignment of data-member 'Item::y' in read-only structure
//    error: passing 'const Item' as 'this' argument of 'void Item::update()' discards qualifiers

        m_items->at(itemMoved).update();
        update();
    }
}

I would make my Item inherit QGraphicsItem but then I get errors about virtual functions that I don't know how to define (like boundingRect which would depend on the item contents... could be objects, images, svg, text... for some i know how to get the bounding rectangle but for others really idk)... Is that the only way to do this ?

How can I identify he items at the location of the mouse position, and what is preventing me to change the x and y for the item once mouse is moved ?

Upvotes: 2

Views: 8054

Answers (1)

If you're going to implement everything yourself, you shouldn't be using QGraphicsView at all. If you wish to use QGraphicsView, there's no need to reimplement any of its virtual methods. Just use it as-is, and set the item's QGraphicsItem::ItemIsMovable flag.

A complete example is provided in this answer. The only reason for reimplementation of QGraphicsView::mousePressEvent was to implement creation of new items.

Upvotes: 2

Related Questions