0
votes

When you get get a mouse signal from a model into your slot, the argument passed is a QModelIndex.

QModelIndex does not tell you what button is pressed. So, we can resort to QApplication::mouseButtons. But QApplication::mouseButtons is the current button press, not when model experienced the click.

My thought experiment is saying that, after the right-button is pressed, the underlying view sends the signal to my widget, but just before my widget's slot received the signal, a spurious left-click occurred. So calling QApplication::mouseButtons on receipt of QModelIndex would wrongly associate the row being click with the left mouse button rather than the right button. How possible is this scenario?

When you look at Qt and even QML, it takes a lot of code acrobatics to achieve proper mouse button info on receipt of a QModelIndex. Is it a policy that nokia is striving to promote mouse button agnosticism?

1

1 Answers

3
votes

I don't think this is a very possible scenario but it may happen.

A "simple" way to be sure about which button was clicked is to subclass QTableView (or the view you are using and reimplement the mouseReleaseEvent.

void mouseReleaseEvent(QMouseEvent * event)
{
    // store the button that was clicked
    mButton = event->button();
    // Now call the parent's event
    QTableView::mouseReleaseEvent(event);
}

By default the mouseReleaseEvent emits the clicked signal if an item of the view is pressed

If a user presses the mouse inside your widget and then drags the mouse to another location before releasing the mouse button, your widget receives the release event. The function will emit the clicked() signal if an item was being pressed.

The trick is to catch the clicked signal in your derived class and emit a new signal which except the model index will contain the button as well.

// Define your new signal in the header
signals:
    void clicked(QModelIndex, Qt::MouseButton);

// and a slot that will emit it
private slots:
    void clickedSlot(QModelIndex); 

// In the constructor of your derived class connect the default clicked with a slot 
connect(this, SIGNAL(clicked(QModelIndex), this, SLOT(clickedSlot(QModelIndex)));

// Now the slot just emits the new clicked signal with the button that was pressed
void clickedSlot(QModelIndex i)
{
    emit clicked(i, mButton);
}

You can do something similar with the mousePressEvent if you need the pressed signal as well.