I managed to achieve what I want by subclassing QPushButton
and QMennu
:
class MyMenu(QtGui.QMenu):
""" Custom menu which will close when mouse is released. ""'"
def mouseReleaseEvent(self, event):
action = self.actionAt(event.pos())
self.triggered.emit(action)
self.close()
class MyButton(QtGui.QPushButton):
triggered = QtCore.pyqtSignal("QAction")
def __init__(self, menu=None, parent=None):
super(MyButton, self).__init__(parent)
self.setMenu(menu)
def menu(self):
return self._menu
def setMenu(self, menu):
self._menu = menu if menu else MyMenu(self)
self._menu.triggered.connect(self.triggered.emit)
and in the QDialog
containing this button, I do the following:
menu = MyMenu(self)
# insert here code to add actions to menu
self.open_btn = MyButton(parent=self, menu=menu)
self.open_btn.pressed.connect(self._onOpenBtnPressed)
self.open_btn.triggered.connect(self._onOpenBtnTriggered)
def _onOpenBtnPressed(self):
# insert here code to check whether we should pop up the menu
pos = self.mapToGlobal(self.open_btn.pos())
pos.setY(pos.y() + self.open_btn.height())
self.open_btn.menu().move(pos)
self.open_btn.menu().show()
def _onOpenBtnTriggered(self, action):
if action:
application_name = str(action.text())
# insert here code to launch this application
else:
# insert here code to launch the default application
self.close() # close this dialog