Qt WheelEvent, how to get if the wheel is pressed? - c++

i'm developing a Qt application, I know that there is a wheelEvent to get the wheel's state, but I can't find how to know if the wheel is pressed.
thanks !

The wheel event set up the buttons which are being pressed. It also set the keyboard modifier keys which are pressed (eg. SHIFT, CRTL).
void MyWidget::wheelEvent ( QWheelEvent * event )
{
if(event->buttons() & Qt::MiddleButton != 0)
{
//the mid button is being pressed. handle.
}
}
Here is a list of possible buttons. They are set as flags, i.e Qt::LeftButton | Qt::RightButton
Edit:
The wheel is associated by default to the middle button. The wheel can move without an associated button in the wheel event. For instance, on chrome browsers moving the wheel scrolls. Pressing the wheel will change the cursor on the screen as well as the behavior of the wheel(try it).
If you have a weird mouse with a wheel and a middle button:
Pressing the middle button will generate a MouseEvent with Qt::MiddleButton
Pressing the wheel button will generate a WheelEvent with Qt::MiddleButton.

Look in the documentation of QMouseEvent. Catch that event and watch out for the third mouse button.
If you are not interested in an event but the state of the button you also may be interested in QGuiApplication::mouseButtons().

Related

Qt: Ignore MouseButtonRelease events when widget is hidden

The Documentation for QWidget says this:
mouseReleaseEvent() is called when a mouse button is released. A
widget receives mouse release events when it has received the
corresponding mouse press event. This means that if the user presses
the mouse inside your widget, then drags the mouse somewhere else
before releasing the mouse button, your widget receives the release
event. There is one exception: if a popup menu appears while the mouse
button is held down, this popup immediately steals the mouse events.
It also says this:
If you create new widgets in the mousePressEvent() the
mouseReleaseEvent() may not end up where you expect, depending on the
underlying window system (or X11 window manager), the widgets'
location and maybe more
In my programme, the is a context where the user can change the current visible widget by pressing Enter. If they click and hold on a toolbar button and press enter while the mouse is still pressed, they can send the mouse release event to the now hidden widget. This is a problem as the actions in the toolbar of the now hidden page, relate to a state which has been deinitialised when the active widget was changed.
The desired behaviour would be for the changing of active widget to somehow 'cancel' or 'release' the old widget's claim to the coming mouse release event even though it (or one of its children) received the corresponding mouse press event, and for the action in the toolbar not to be triggered.
Is there any way to do this? Or does anyone have any guidance on what I might be looking for?
Thanks
One options is by creating eventFilter function (either in widget itself (if your own) or parent widget), installing it with installEventFilter and then checking for mouse release event type and only accept the event if widget's isVisible() returns true.
Another option (in case you have your own Qt based widget class) is to override mouseReleaseEvent and do the same visibility check in there.

catch mouse motion in gtkmm

I am trying to catch the mouse motion when I hold the mouse middle button. The goal is to implement a rotation feature in an stl viewer.
I found the event mask BUTTON2_MOTION_MASK. But I have a hard time figuring out which signal catches it.
Here's the two line I use to create and hook the event. These two line are inside a GtkApplicationWindow Constructor.
glWidget.add_events(Gdk::BUTTON2_MOTION_MASK);
glWidget.signal_motion_notify_event().connect(sigc::mem_fun(*this,&mainWindow::rotate));
Here's the function I am trying to connect.
bool mainWindow::rotate(GdkEventMotion* motion_event)
{
cout<<"test"<<endl;
}
Am I using the correct method? The code does not react when I hold the middle mouse button and move mouse.
I managed to get glArea widget to react to scrolling this way.
glWidget.add_events(Gdk::SMOOTH_SCROLL_MASK);
glWidget.signal_scroll_event().connect(sigc::mem_fun(*this,&mainWindow::zoom));
the function I connected:
bool mainWindow::zoom(GdkEventScroll *eventScroll)
{
cout<<"test"<<endl;
return true;
}
I figured it out. You need to both add the Gdk::Button1_MOTION_MASK and the Gdk::BUTTON_PRESS_MASK.
glWidget.add_events(Gdk::Button1_MOTION_MASK | Gdk::BUTTON_PRESS_MASK);
This will catch the signal when the left mouse button is clicked and positioned on the widget.
BUTTON2_MOTION_MASK will require that 2 button are pressed. For some reason, it's only the left mouse button(I want the middle button).

How to set QTextEdit to only start editing on mouse click/release?

I tried setFocusPolicy(Qt::TabFocus); but the cursor starts flashing and gets focus as soon as the mouse is pressed on it.
Is there a way to change it to mouse click?
I'm using Qt 4.6.3 on a touch screen device.
When QTextEdit gets the focus, then the KineticScroller stops working.
What I want to achieve:
1) On mouse press event QTextEdit does nothing.
2) On mouse release event, if the release is within the rect() of QTextEdit, then it gets focus and start editing.
3) If not in rect() don't do anything.
I know how to acheive 2) and 3) by rewriting mousePressEvent() and mouseReleaseEvent() but I have no I idea how not to let it get focus on mouse press.
Can someone share some thoughts on why setFocusPolicy(Qt::TabFocus); doesn't do this for me?

C++ CLI GUI Event Handeling

I am working on a c++ CLI application and am having some difficulty with events. I am wondering if I can get events to fire while the mouse button is clicked. For example, I am wanting to check whether or not the mouse has moved to the next square over only if they have the mouse clicked in. Meaning if they click on square 1 they should be able to hold that click and move the square 2 and my program recognize this.
I have run a number of different events on the mouse, including the "Click" event, but the neither the hover, mouse enter, or mouse down event get triggered while the button is pressed. The "MouseClick" event, which does the same. I tried using just the mouseDown event, but this does not let another mouseDown event, mouse enter, or hover event fire.
Short of checking mouse position I do not know what I can do. I would like to not have to do mouse position checking.
If anyone has any ideas, they would be greatly appreciated.
Clearly you'll want to pay attention to the MouseMove event so you can see the mouse moving into another square. Roughly:
void panel1_MouseMove(Object^ sender, MouseEventArgs^ e) {
if ((e->Button & System::Windows::Forms::MouseButtons::Left) ==
System::Windows::Forms::MouseButtons::Left) {
int square = MapPosToSquare(e->Location);
if (square != currentSquare) {
currentSquare = square;
OnSquareClicked(currentSquare);
}
}
}
If these "squares" are actually controls then you have a different problem. You have to set the control's Capture property to false in the MouseDown event handler so it doesn't capture the mouse.

Win32 : How to trap left and right mouse button clicked at the same time

I am trying to program specific behaviour when the user (clicks and) releases the left and right mouse at the same time. Is there a known way to trap such an event / gesture. I am aware of how to trap leftButtonUp and rightButtonUp but not sure how I can trap this event.
If the left button is pressed and then the right button is pressed with a delta delay, that is OK. When the user releases the right button / left button and if this is followed up by release of other button within a defined epsilon time then such an event should be raised.
There is no such event in WinAPI, but you may track it yourself. wParam of all button down/up messages contains information of the state of all buttons at the time of event:
MK_LBUTTON 0x0001 The left mouse button is down.
MK_MBUTTON 0x0010 The middle mouse button is down.
MK_RBUTTON 0x0002 The right mouse button is down.
Thus, you need to keep the track of changes and define a threshold that will filter out all events that you like to consider as a "simultaneous click/release"
You will need to write your own method of handling this. Record when the first button was clicked, when the other button is clicked see if the first button is still down and if the delay is less than whatever delta you've supplied.
If GetAsyncKey(0x01) && GetAsyncKey(0x02){
DoEvent();
}